集合操作(STL&逆向)
如果正向儲存當前集合的元素的話,查詢時會很麻煩。所以我們反向考慮,我們用一個集合儲存集合中每個元素的最小未出現的元素(即x+1)
然後我們需要用一個來標記該元素是否在題意的集合中。
對於操作1,我們只需判斷是否出現過,如果沒出現過就加到中,在判斷是否在集合中出現過,若出現過就刪掉。對於操作2,就直接加入到中。
然後對於操作3,如果不在題意集合中就直接輸出,否則二分一下集合中的元素即可。
時間複雜度:
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const int N=1e5+5;
#define mst(a) memset(a,0,sizeof a)
unordered_map<int,bool>mp;
set<int>s;
int main(){
int n,op,x;
scanf("%d",&n);
for(int i=1;i<=n;i++){
scanf("%d%d",&op,&x);
if(op==1){
mp[x]=1;
if(!mp[x+1]) s.insert(x+1);
if(s.count(x)) s.erase(x);
}
else if(op==2) s.insert(x);
else {
if(!mp[x]) printf("%d\n",x);
else printf("%d\n",*(s.lower_bound(x)));
}
}
return 0;
}