[BZOJ4994][Usaco2017 Feb]Why Did the Cow Cross the Road III(树状数组)
越来越写不来简单题了。
就是求a[i]到b[i]之间的位置有多少个数是第一次出现且目前仅出现了一次。树状数组,每次给第一次出现的数的位置+1,若到了第二次出现的位置,则将第一次出现的位置-1即可。
1 #include<cstdio> 2 #include<algorithm> 3 #define rep(i,l,r) for (int i=(l); i<=(r); i++) 4 typedef long long ll; 5 using namespace std; 6 7 const int N=100010; 8 int n,x,ans,p[N],c[N]; 9 10 void add(int x,int k){ for (int i=x; i<=2*n; i+=i&-i) c[i]+=k; } 11 int que(int x){ int res=0; for (int i=x; i; i-=i&-i) res+=c[i]; return res; } 12 13 int main(){ 14 scanf("%d",&n); 15 rep(i,1,2*n){ 16 scanf("%d",&x); 17 if (!p[x]) p[x]=i,add(i,1); 18 else add(p[x],-1),ans+=que(i)-que(p[x]); 19 } 20 printf("%d\n",ans); 21 return 0; 22 }