P1059 [NOIP2006 普及组] 明明的随机数---题解
题目描述
明明想在学校中请一些同学一起做一项问卷调查,为了实验的客观性,他先用计算机生成了NN个11到10001000之间的随机整数(N≤100)(N≤100),对于其中重复的数字,只保留一个,把其余相同的数去掉,不同的数对应着不同的学生的学号。然后再把这些数从小到大排序,按照排好的顺序去找同学做调查。请你协助明明完成“去重”与“排序”的工作。
输入格式
输入有两行,第11行为11个正整数,表示所生成的随机数的个数NN
第22行有NN个用空格隔开的正整数,为所产生的随机数。
输出格式
输出也是两行,第11行为11个正整数MM,表示不相同的随机数的个数。
第22行为MM个用空格隔开的正整数,为从小到大排好序的不相同的随机数。
输入输出样例
10 20 40 32 67 40 20 89 300 400 15
8 15 20 32 40 67 89 300 400
说明/提示
NOIP 2006 普及组 第一题
这道题的话呢~用桶排序的话是比较好做的,可能好多人不知道桶排序是种什么排序算法,那我们先来了解一下桶排序吧~
桶排序的思想就是:首先遍历一遍数组,找出数组中值最大的元素,假设最大的元素为Max;然后定义Max+1个“桶”,可以用“队列”或“栈”来定义;之后再遍历一遍数组,将元素值为i的元素放在第i个桶中;最后从第0个桶开始遍历,将桶中的元素依次放入原有数组中,直到遍历到第Max个桶为止。由此可见,桶排序目的是以扩大内存空间为代价,从而减少时间复杂度。但是假若数组中的元素很少,而数组中值最大的元素非常大的时候,用这种算法显然也不能减少时间复杂度,故实际中很少用到这种排序算法。此外,对于浮点型的数据,这种算法就非常不适合,除非找到桶的下标(因为桶的下标为整型)与数值精度的映射关系。在桶排序的基础上,对该算法进行了改进,产生了“基数排序”
当我们知道桶排序之后,我们就可以很简单的解决这种题了。
本题讲解:1.首先开辟一个数组空间,全部初始化成0;(还有一些自定义的变量和计数器这里就不说了,知道就行)
2.判断数组的这个位置有没有数,如果有就continue;没有就把这个位置变成1;
3.判断当期位置是不是1,如果是输出当前这个数,没有就接着继续。
参考代码:
#include<iostream> #include <cstdio> using namespace std; int main(){ int n,x; scanf("%d",&n); int sum(0),bus[1002]={0}; for(int i=1;i<=n;i++){ cin>>x; if(bus[x]) continue; bus[x]++; sum++; } printf("%d\n",sum); for(int i=1;i<=1000;i++) if(bus[i]) printf("%d %",i);
return 0; }