有一个整数集合,初始时集合为空。
现在,要对该集合进行 t 次操作,操作分为以下三种:
+ x
,将一个非负整数 x 添加至集合中。注意,集合中可以存在多个相同的整数。- x
,从集合中删除一个非负整数 x。可以保证执行此操作时,集合中至少存在一个 x。? s
,询问操作,给定一个由 0 和 1 组成的模板 s,请你计算并输出此时集合中有多少个元素可以与 s 相匹配。
关于判断整数 x 与模板 s 是否匹配的具体方法如下:
- 首先,在进行匹配判断前,应保证 x 与 s 位数相同,如果两者位数不同,则位数更少的一方需补充前导 0 至与位数更多的一方位数相同为止。
- 从最高位开始,对每一位进行逐个判断,如果 s 的第 i 位为 0,则 x 的第 i 位必须为偶数,如果 s 的第ii 位为 1,则 x 的第 i 位必须为奇数。
- 如果有任意一位不满足上述条件,则视为 x 与 s 不匹配。如果所有位均满足上述条件,则视为 x 与 s 匹配。
输入格式
第一行包含整数 t,表示操作次数。
接下来 t 行,每行包含一个操作,格式如题面描述。
保证至少存在一个查询操作。
输入样例1:
12
+ 1
+ 241
? 1
+ 361
- 241
? 0101
+ 101
? 101
- 101
? 101
+ 4000
? 0
输出样例1:
2
1
2
1
1
输入样例2:
5
+ 200
+ 200
? 0
- 200
? 0
输出样例2:
2
1
#include <bits/stdc++.h>
#define LL long long
using namespace std;
const int maxn = 1e6 + 10;
const int mod = 1e9 + 7;
const int INF = 1e9 + 10;
const int N = 1 << 18;
int n;
int cnt[N];
int main(){
cin >> n;
char op[2],str[20];
while(n--){
scanf("%s%s",op,str);
int x = 0;
for(int i = 0;str[i];i++){
x = x * 2 + str[i] % 2;
}
if(*op == '+') cnt[x] ++;
else if(*op == '-') cnt[x]--;
else cout << cnt[x] << endl;
}
return 0;
}