bzoj2658 [Zjoi2012]小蓝的好友(mrx)
坑坑坑坑
我自己怎么想都不会把一列当成一个点写平衡树QAQ
扫描线+可持久化treap
showson教了我可持久化treap%%%
1 #include<algorithm> 2 #include<iostream> 3 #include<cstdlib> 4 #include<cstring> 5 #include<cstdio> 6 #include<string> 7 #include<cmath> 8 #include<ctime> 9 #include<queue> 10 #include<stack> 11 #include<map> 12 #include<set> 13 #define rre(i,r,l) for(int i=(r);i>=(l);i--) 14 #define re(i,l,r) for(int i=(l);i<=(r);i++) 15 #define Clear(a,b) memset(a,b,sizeof(a)) 16 #define inout(x) printf("%d",(x)) 17 #define douin(x) scanf("%lf",&x) 18 #define strin(x) scanf("%s",(x)) 19 #define LLin(x) scanf("%lld",&x) 20 #define op operator 21 #define CSC main 22 typedef unsigned long long ULL; 23 typedef const int cint; 24 typedef long long LL; 25 using namespace std; 26 void inin(int &ret) 27 { 28 ret=0;int f=0;char ch=getchar(); 29 while(ch<'0'||ch>'9'){if(ch=='-')f=1;ch=getchar();} 30 while(ch>='0'&&ch<='9')ret*=10,ret+=ch-'0',ch=getchar(); 31 ret=f?-ret:ret; 32 } 33 LL S(LL x){return x*(x+1)>>1;} 34 int root,s[40040],h[40040],tag[40040],ch[40040][2],ed; 35 LL ans[40040]; 36 int newnode(int x) 37 { 38 s[++ed]=1,h[ed]=x,ans[ed]=tag[ed]=0; 39 return ed; 40 } 41 void maintain(int k) 42 { 43 if(!k)return ; 44 s[k]=s[ch[k][0]]+s[ch[k][1]]+1; 45 ans[k]=0; 46 re(i,0,1)ans[k]+=ans[ch[k][i]]+S(s[ch[k][i]])*(h[ch[k][i]]-h[k]); 47 } 48 void add(int k,int d) 49 { 50 if(!k)return ; 51 h[k]+=d,tag[k]+=d; 52 } 53 void down(int k) 54 { 55 add(ch[k][0],tag[k]); 56 add(ch[k][1],tag[k]); 57 tag[k]=0; 58 } 59 int merge(int l,int r) 60 { 61 if(!l||!r)return l+r; 62 if(h[l]<h[r]) 63 { 64 down(l); 65 ch[l][1]=merge(ch[l][1],r); 66 maintain(l); 67 return l; 68 } 69 down(r); 70 ch[r][0]=merge(l,ch[r][0]); 71 maintain(r); 72 return r; 73 } 74 pair<int,int> split(int k,int l) 75 { 76 if(!k)return pair<int,int>(0,0); 77 pair<int,int> wocao; 78 down(k); 79 if(s[ch[k][0]]>=l) 80 { 81 wocao=split(ch[k][0],l); 82 ch[k][0]=wocao.second; 83 wocao.second=k; 84 } 85 else 86 { 87 wocao=split(ch[k][1],l-s[ch[k][0]]-1); 88 ch[k][1]=wocao.first; 89 wocao.first=k; 90 } 91 maintain(k); 92 return wocao; 93 } 94 pair<int,int> p[100010]; 95 int main() 96 { 97 int r,c,n; 98 inin(r),inin(c),inin(n); 99 re(i,1,n)inin(p[i].first),inin(p[i].second); 100 sort(p+1,p+n+1); 101 re(i,1,c)root=merge(root,newnode(0)); 102 LL an=S(r)*S(c); 103 int j=1; 104 re(i,1,r) 105 { 106 add(root,1); 107 while(j<=n&&p[j].first==i) 108 { 109 int x=p[j++].second; 110 pair<int,int> r1=split(root,x-1),r2=split(r1.second,1); 111 h[r2.first]=0; 112 root=merge(merge(r1.first,r2.first),r2.second); 113 } 114 an-=ans[root]+S(s[root])*h[root]; 115 } 116 printf("%lld",an); 117 return 0; 118 }