您的位置:首页 > 其它

统计数字题解

2016-02-03 20:30 525 查看

描述
某次科研调查时得到了n个自然数,每个数均不超过1500000000(1.5*109)。已知不相同的数不超过10000个,现在需要统计这些自然数各自出现的次数,并按照自然数从小到大的顺序输出统计结果。

输入包含n+1行:

第一行是整数n,表示自然数的个数;

第2~n+1每行一个自然数。

40%的数据满足:1<=n<=1000;

80%的数据满足:1<=n<=50000;

100%的数据满足:1<=n<=200000,每个数均不超过1500 000 000(1.5*10^9)。输出包含m行(m为n个自然数中不相同数的个数),按照自然数从小到大的顺序输出。每行输出两个整数,分别是自然数和该数出现的次数,其间用一个空格隔开。

解:

由于题目说每个数均不超过1500000000,则数组可只开int整形。由于输入数据并没有必要全部储存下来,因此在循环中全部在变量a中输入,边输入边记录出现次数。为了又能记数字,还能记次数,直接开一个二维数组b,用k来记录下标。每次输入a后,就通过循环找b中是否已经储存数字a,若有,则在相应下标的第二格即次数+1,若没有,则k+1,在b[k][0]中存入a将次数记为1。循环完成后,为了满足题目中按数字大小顺序输出还需将b数组进行排序再输出。

参考代码:
#include<cstdio>
#include<cstdlib>
#include<cstring>

int b[10001][2];

void f(int m,int n,int key)
{
if(m<=n)
{
return;
}
int r=m,l=n,i=b[key][0],j=b[key][1];
while(r>l)
{
while(r>l&&b[r][0]>i)
{
r--;
}
b[l][0]=b[r][0];
b[l][1]=b[r][1];
while(r>l&&b[l][0]<i)
{
l++;
}
b[r][0]=b[l][0];
b[r][1]=b[l][1];
}
b[l][0]=i;
b[l][1]=j;
f(m,l+1,l+1);
f(l-1,n,n);
}

int main()
{
int n,k=0,flag=0;
scanf("%d",&n);
int a;
for(int i=1;i<=n;i++)
{
scanf("%d",&a);
for(int j=1;j<=k;j++)
{
if(a==b[j][0])
{
flag=1;
b[j][1]++;
break;
}
}
if(flag==0)
{
k++;
b[k][0]=a;
b[k][1]=1;
}
flag=0;
}
f(k,1,1);
for(int i=1;i<=k;i++)
{
printf("%d %d\n",b[i][0],b[i][1]);
}
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: