原题链接:传送门
这道题我最开始是用的map标记来写的,但写完后发现TLE了,后来看别人的题解才知道是要用哈希来做,就学了一下哈希。但还是不太明白,为啥map标记会超时??
这里贴个用map写的TLE了的代码。。
#include <iostream>
#include <cstring>
#include <cstdio>
#include <map>
using namespace std;
map<int,int> M;
int main() {
int t;
char str[8];
scanf("%d",&t);
while(t--) {
int n,x;
scanf("%s %d",str,&n);
if(str[0] == 'A') {
for(int i=0; i<n; i++) {
scanf("%d",&x);
M[x] = 1;
}
} else {
for(int i=0; i<n; i++) {
scanf("%d",&x);
if(M[x] == 1) {
printf("YES\n");
} else printf("NO\n");
}
}
}
return 0;
}
AC代码:
#include <iostream>
#include <cstring>
#include <cstdio>
using namespace std;
const int N = 1000002;
const int fib = 100001; //尽量是个稍微大一点的素数,以随机散列
int Hash[N],Head[N],Next[N]; //Head相当于每个哈希表的头节点,Next指向当前节点的下一个节点
int top;
void Add(int x) {
int key = x % fib;
Next[top] = Head[key]; //关键就是这。可以手动模拟一下。
Head[key] = top;
Hash[top] = x;
top ++;
}
bool Query(int x) {
int key = x % fib;
for(int i=Head[key]; i>-1; i=Next[i]) { //如果有多个数散射后的特征值相同,会接着往下找
if(Hash[i] == x) {
return true;
}
}
return false;
}
int main() {
int t,n,x;
char str[8];
scanf("%d",&t);
memset(Head,-1,sizeof(Head));
top = 0;
while(t--) {
scanf("%s %d",str,&n);
// scanf("%d",&n);
if(str[0] == 'A') {
for(int i=0; i<n; i++) {
scanf("%d",&x);
Add(x);
}
} else {
for(int i=0; i<n; i++) {
scanf("%d",&x);
if(Query(x)){
printf("YES\n");
}
else printf("NO\n");
}
}
}
return 0;
}