码迷,mamicode.com
首页 > 其他好文 > 详细

暑期集训第六天(6-27)自由复习的题目练习及总结

时间:2020-06-27 19:58:42      阅读:58      评论:0      收藏:0      [点我收藏+]

标签:就是   nbsp   code   date   现在   lse   ||   open   alt   

今天时间本来是很充裕的,毕竟不考试留出了一天的时间进行整理,直到我发现我打完替罪羊树编译报错一大堆(往上滑都要十多秒的那种),还没有调试就已经10点多快十一点的那一刻......郭大佬还是你郭大佬,后来我问他他说这道题他就写了一个多不到两个小时就过了......而我直到现在都还没调完,上午写完后心态直接爆炸,就去做其他的题了,下午又调了将近一个小时,只得了三分之一的分数,持续烦躁,就和后排的三个大神一起去水洛谷了,以后每天抽大概一个小时调一调,最好再重新写一遍吧,毕竟郭大佬也是写了一遍,重构了一遍(话说今天洛谷说我不宜重构代码???),我先把我的一上午的辛苦成果放在这吧,有大佬帮我调一调,纠纠错当然更好.

技术图片
  1 #include<bits/stdc++.h>
  2 const int N=1e5+10;
  3 struct Tree{
  4     int l,r,x,tot,siz,yxsiz,gssiz,fa;
  5                     //yx-有效 gs-个数
  6     bool del;
  7 }tree[N];
  8 double balance=0.75;
  9 int len,shan[N],t,root;
 10 int newp(){
 11     if(t>0) return shan[t--];
 12     return ++len;
 13 }
 14 void build(int x,int y,int fa){
 15     tree[y].x=x;tree[y].l=tree[y].r=0;tree[y].tot=1;
 16     tree[y].del=false;tree[y].fa=fa;
 17     tree[y].siz=tree[y].yxsiz=tree[y].gssiz=1;
 18 }
 19 int find(int x,int root){
 20     if(x<tree[root].x&&tree[root].l) return find(x,tree[root].l);
 21     if(x>tree[root].x&&tree[root].r) return find(x,tree[root].r);
 22     return root;
 23 }
 24 void update(int now,int x,int y,int z){
 25     if(!now) return;
 26     tree[now].siz+=x;
 27     tree[now].yxsiz+=y;
 28     tree[now].gssiz+=z;
 29     update(tree[now].fa,x,y,z);
 30 }
 31 struct Node{
 32     int x,tot;
 33 }num[N];
 34 int num_tot=0;
 35 void dfs_rebuild(int x)
 36 {
 37     if(x==0) return;
 38     dfs_rebuild(tree[x].l);
 39     if(!tree[x].del)num[++num_tot].x=tree[x].x,num[num_tot].tot=tree[x].tot;
 40     shan[++t]=x;
 41     dfs_rebuild(tree[x].r);
 42 }
 43 int readd(int l,int r,int fa){
 44     if(l>r) return 0;
 45     int mid=(l+r)>>1;int id=newp();
 46     tree[id].fa=fa;
 47     tree[id].tot=num[mid].tot;
 48     tree[id].x=num[mid].x;
 49     tree[id].l=readd(l,mid-1,id);
 50     tree[id].r=readd(mid+1,r,id);
 51     tree[id].gssiz=tree[tree[id].l].gssiz+tree[tree[id].r].gssiz+num[mid].tot;
 52     tree[id].siz=tree[id].yxsiz=r-l+1;
 53     tree[id].del=false;
 54     return id;
 55 }
 56 void rebuild(int x){
 57     num_tot=0;
 58     dfs_rebuild(x);
 59     if(x==root) root=readd(1,num_tot,0);
 60     else{
 61         update(tree[x].fa,-tree[x].siz+tree[x].yxsiz,0,0);
 62         if(tree[tree[x].fa].l==x) tree[tree[x].fa].l=readd(1,num_tot,tree[x].fa);
 63         else tree[tree[x].fa].r=readd(1,num_tot,tree[x].fa);
 64     }
 65 }
 66 void find_rebuild(int now,int x){
 67     if((double)tree[tree[now].l].siz>(double)tree[now].siz*balance ||
 68     (double)tree[tree[now].r].siz>(double)tree[now].siz*balance ||
 69     (double)(tree[now].siz-(double)tree[now].yxsiz)>(double)tree[now].siz * 0.4){
 70         rebuild(now);return;
 71     }
 72     if(tree[now].x!=x) find_rebuild(x<tree[now].x ? tree[now].l : tree[now].r,x);
 73 }
 74 void Add(int x){
 75     if(root==0){
 76         build(x,root=newp(),0);
 77         return;
 78     }
 79     int p=find(x,root);
 80     if(tree[p].x==x){
 81         tree[p].tot++;
 82         if(tree[p].del) tree[p].del=0,update(p,0,1,1); 
 83         else update(p,0,0,1);
 84     }
 85     else if(x<tree[p].x){
 86         build(x,tree[p].l=newp(),p);update(p,1,1,1);
 87     }
 88     else build(x,tree[p].r=newp(),p),update(p,1,1,1);
 89     find_rebuild(root,x);
 90 }
 91 void del(int x){
 92     int p=find(x,root);
 93     tree[p].tot--;
 94     if(!tree[p].tot){
 95         tree[p].del=1;
 96         update(p,0,-1,-1);
 97     }
 98     else update(p,0,0,-1);
 99     find_rebuild(root,x);
100 }
101 void query_rank(int x){//
102     int now=root;
103     int ans=0;
104     while(tree[now].x!=x){
105         if(x>=tree[now].x){
106             ans+=tree[tree[now].l].gssiz+tree[now].tot;
107             now=tree[now].r;
108         }
109         else{
110             now=tree[now].l;
111         }
112     }
113     ans+=tree[tree[now].l].yxsiz;
114     printf("%d\n",ans+1);
115 }
116 void query_num(int rank){
117     int now=root;
118     while(1){
119         if(rank<=tree[tree[now].l].gssiz) now=tree[now].l;
120         else{
121             rank-=tree[tree[now].l].gssiz;
122             if(rank<=tree[now].tot){
123                 printf("%d\n",tree[now].x);
124                 return;
125             }
126             rank-=tree[now].tot;now=tree[now].r;
127         }
128     }
129 }
130 bool ans=0;
131 void dfs_lson(int x){
132     if(tree[x].r!=0) dfs_lson(tree[x].r);
133     if(ans) return;
134     if(!tree[x].del){
135         ans=1;
136         printf("%d\n",tree[x].x);
137         return;
138     }
139     if(tree[x].l!=0) dfs_lson(tree[x].l);
140 }
141 void dfs_rson(int x){
142     if(tree[x].l!=0) dfs_rson(tree[x].l);
143     if(ans) return;
144     if(!tree[x].del){
145         ans=1;
146         printf("%d\n",tree[x].x);
147         return;
148     }
149     if(tree[x].r!=0) dfs_rson(tree[x].r);
150 }
151 void query_front(int now,int x,bool lson){
152     if(!lson){
153         query_front(tree[now].fa,x,tree[tree[now].fa].l==now);
154         return;
155     }
156     if(!tree[now].del&&tree[now].x<x){
157         printf("%d\n",tree[now].x);
158         return;
159     }
160     if(tree[now].l){
161         ans=0;
162         dfs_lson(tree[now].l);
163         return;
164     }
165     query_front(tree[now].fa,x,tree[tree[now].fa].l==now);
166 }
167 void query_back(int now,int x,bool rson){
168     if(!rson){
169         query_back(tree[now].fa,x,tree[tree[now].fa].r==now);
170         return;
171     }
172     if(!tree[now].del&&tree[now].x>x){
173         printf("%d\n",tree[now].x);
174         return;
175     }
176     if(tree[now].r){
177         ans=0;
178         dfs_rson(tree[now].r);
179         return;
180     }
181     query_back(tree[now].fa,x,tree[tree[now].fa].r==now);
182 }
183 int main(){
184     //freopen("a.in","r",stdin);
185     int n;
186     scanf("%d",&n);
187     while(n--){
188         int x,y;
189         scanf("%d%d",&x,&y);
190         if(x==1) Add(y);
191         if(x==2) del(y);
192         if(x==3) query_rank(y);
193         if(x==4) query_num(y);
194         if(x==5) query_front(find(y,root),y,true);
195         if(x==6) query_back(find(y,root),y,true);
196     }
197     return 0;
198 }
替罪羊树半成品

技术图片

 

 

 (这么彩的结果,你值得拥有)

先放一下这棵树来说一下今天的练习题吧.

技术图片

 

 

 

 

技术图片

 

技术图片

 

技术图片

 

 看到这个题的第一感觉就是这道题建好图就已经成功了一大半了(某邹姓少年除外,他因为手懒用的STL的栈写的tarjan后来他自己都调不过,后来还是lc大佬调好的)最暴力的建图方式当然是枚举每一个兴奋值在兴趣值之中找到其倍数,之后连边,但是n最大到1e5,n^2的时间效率可能让我们的程序都活不到tarjan部分就挂了,我最先想到的思路是分别枚举兴趣值和兴奋值之中的约数和乘数,如果可以连在约数上的边一定

暑期集训第六天(6-27)自由复习的题目练习及总结

标签:就是   nbsp   code   date   现在   lse   ||   open   alt   

原文地址:https://www.cnblogs.com/li-jia-hao/p/13199493.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!