数星星

【题目描述】

不同的星星有着不同程度的光芒,小明的望远镜可以计算出星星光芒的数值W。

小明每看到一颗星星,就要询问他之前有没有看到过这颗星星。

【输入描述】

输入共两行。

第一行输入一个整数,表示小明观测到的星星的数量n;

第二行输入n个整数,分别表示每颗星星光芒的数值W。

【输出描述】

输出一行,包含n个数字0或1,0表示对应的星星之前没有观测到,1表示对应的星星之前已经观测到了。

【样例输入】

5

1 5 5 4 1

【样例输出】

00101

【数据范围及提示】

对于30%的数据,0 < n ≤ 5000;

对于20%的数据,-20000 ≤ W ≤ 20000;

对于60%的数据,0 < n ≤ 50000;

对于100%的数据,0 < n ≤ 500000;-2000000000 ≤ W ≤ 2000000000。

 

STL威风堂堂!

源代码:

#include<cstdio>
#include<set>
using namespace std;
set <long long> S;
int n;
int main()
{
    scanf("%d",&n);
    for (int a=0;a<n;a++)
    {
        int t;
        scanf("%d",&t);
        printf("%d",!S.insert(t).second);
    }
    return 0;
}

/*
    又是恐怖的STL大显神通。
    set为C++中利用红黑树(RBT)进行集合性操作的模板,其常用操作如下:
        (1)insert():向集合中插入元素,并且可用insert().second判断插入是否成功;
        (2)erase():删除集合中指定的某一元素;
        (3)clear():清空集合中的所有元素;
        (4)size():返回集合中元素的个数;
        (5)empty():判断集合是否为空;
        (6)begin():返回集合的第一个元素;
        (7)end():返回集合的最后一个元素;
        (8)find():检索指定元素,若找到,则返回其迭代器位置,否则,返回最后一个元素的后一位置(end())。
*/

 

哈希表解法:

源代码:

#include<cstdio>
#define INF 300017
struct Node
{
    int S,Next;
}Q[500001];
int n,Num(0),i[300017];
int Hash(int T)
{
    if (T<0) //蛤蛤蛤谁出的题看我打不死你这该死的负数。
      T=-T;
    T%=INF;
    return T;
}
void Add(int T) //类似于边表。
{
    int t=Hash(T); //t表示哈希值。
    Q[++Num].Next=i[t]; //i[]表示此哈希值现存的最后一个节点的编号。
    Q[Num].S=T; //原数值。
    i[t]=Num; //更新i[]。
}
bool Solve(int T) //查找。
{
    int t=Hash(T);
    t=i[t];
    while (t)
    {
        if (Q[t].S==T)
          return true;
        t=Q[t].Next;
    }
    return false;
}
int main()
{
    scanf("%d",&n);
    for (int a=0;a<n;a++)
    {
        int t;
        scanf("%d",&t);
        if (Solve(t))
          printf("1");
        else
        {
            Add(t);
            printf("0");
        }
    }
    return 0;
}

/*
    有必要讲一下Hash Table的常用解法:
        Hash Table的本质就是使一个数模一个定值(最好为素数),然后得到一个哈希值,从而大大节省空间。
        然后以链表或边表的形式存储,最后进行查找。
*/

转载于:https://www.cnblogs.com/Ackermann/p/5929201.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值