【算法题解】明明的随机数

111 阅读2分钟

持续创作,加速成长!这是我参与「掘金日新计划 · 6 月更文挑战」的第4天,点击查看活动详情 

描述

明明生成了N个1到500之间的随机整数。请你删去其中重复的数字,即相同的数字只保留一个,把其余相同的数去掉,然后再把这些数从小到大排序,按照排好的顺序输出。

数据范围:1≤n≤1000  ,输入的数字大小满足 1≤val≤500 

输入描述:

第一行先输入随机整数的个数 N 。 接下来的 N 行每行输入一个整数,代表明明生成的随机数。 具体格式可以参考下面的"示例"。

输出描述:

输出多行,表示输入数据处理后的结果

示例1

输入:

3
2
2
1

输出:

1
2

说明:

输入解释:
第一个数字是3,也即这个小样例的N=3,说明用计算机生成了31500之间的随机整数,接下来每行一个随机数字,共3行,也即这3个随机数字为:
2
2
1
所以样例的输出为:
1
2     

题目的主要信息:

  • 一共多次调查,每次调查输入的第一个数为N,后续N个数随机(1-1000)的数字
  • 需要对每次调查数字排序并去重后输出,每个数字一行

方法一:暴力排序去重

具体做法:

我们每次循环优先读取下面的数组长度,即优先读取N,然后用循环连续N个数字进入数字,这就是这次调查的全部数字了,然后我们使用sort函数快排对这些数字排序,排好序后我们就可以输出了,需要注意除了第一个元素外我们都要检查是否和前一个元素相等,相等我们就不输出,这样来去重。

#include<iostream>
#include<vector>
#include<algorithm>
using namespace std;

int main(){
    int n;
    while(cin >> n){ //首先输入每次调查的人数n
        vector<int> v(n);
        for(int i = 0 ; i < n; i++) //连续输入n个整数
            cin >> v[i];
        sort(v.begin(), v.end()); //排序
        for(int i = 0; i < n; i++){ //去重输出
            if(i != 0 && v[i] == v[i - 1])
                continue;
            else
                cout << v[i] << endl;
        }
    }
    return 0;
}

复杂度分析:

  • 时间复杂度:O(nlog2n)O(nlog_2n),n为输入的总数字个数,输入输出都是一次遍历,而排序是分段排序,最坏情况下才是O(nlog2n)O(nlog_2n)
  • 空间复杂度:O(n)O(n),n为输入的总数字个数,中途记录数据的数组最坏情况下长度为n−1

方法二:有序集合

具体做法:

读取数据的方式和方法一一致,但是我们这里不采用数组来记录数字,而是采用set。set作为集合它可以对添加的数据自动去重,而且依赖于红黑树的它内部是有序,我们也省去了排序的操作,最后直接遍历set,输出即可。需要注意,每次要清空set中的内容,避免上次调查的数据用到了这次。

#include<iostream>
#include<set>
#include<algorithm>
using namespace std;

int main(){
    int n;
    set<int> s;
    while(cin >> n){ //首先输入每次调查的人数n
        s.clear(); //每次调查清空集合
        for(int i = 0 ; i < n; i++){
            int temp;
            cin >> temp;  //连续输入n个整数
            s.insert(temp);  //插入集合中,自动排序去重
        }
        for(auto iter = s.begin(); iter != s.end(); iter++) //遍历集合直接输出即可
            cout << *iter << endl;
    }
    return 0;
}

复杂度分析:

  • 时间复杂度:O(nlog2n)O(nlog2n),n为输入的总数字个数,set依赖于红黑树,每次插入都是O(log2n)O(log_2n),最坏情况下只有一个数组,需要O(nlog2n)O(nlog_2n)
  • 空间复杂度:O(n)O(n),n为输入的总数字个数,最坏情况下set大小为n−1