BZOJ1782[USACO 2010 Feb Gold 3.Slowing down]——dfs+treap
生活随笔
收集整理的這篇文章主要介紹了
BZOJ1782[USACO 2010 Feb Gold 3.Slowing down]——dfs+treap
小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.
題目描述
每天Farmer John的N頭奶牛(1 <= N <= 100000,編號(hào)1…N)從糧倉(cāng)走向他的自己的牧場(chǎng)。牧場(chǎng)構(gòu)成了一棵樹(shù),糧倉(cāng)在1號(hào)牧場(chǎng)。恰好有N-1條道路直接連接著牧場(chǎng),使得牧場(chǎng)之間都恰好有一條路徑相連。第i條路連接著A_i,B_i,(1 <= A_i <= N; 1 <= B_i <= N)。奶牛們每人有一個(gè)私人牧場(chǎng)P_i (1 <= P_i <= N)。糧倉(cāng)的門(mén)每次只能讓一只奶牛離開(kāi)。耐心的奶牛們會(huì)等到他們的前面的朋友們到達(dá)了自己的私人牧場(chǎng)后才離開(kāi)。首先奶牛1離開(kāi),前往P_1;然后是奶牛2,以此類推。當(dāng)奶牛i走向牧場(chǎng)P_i時(shí)候,他可能會(huì)經(jīng)過(guò)正在吃草的同伴旁。當(dāng)路過(guò)已經(jīng)有奶牛的牧場(chǎng)時(shí),奶牛i會(huì)放 慢自己的速度,防止打擾他的朋友。 考慮如下的牧場(chǎng)結(jié)構(gòu)(括號(hào)內(nèi)的數(shù)字代表了牧場(chǎng)的所有者)。輸入
* 第1行 : 一個(gè)正整數(shù)N * 第2…N行: 第i+1行包括一對(duì)正整數(shù)A_i,B_i * 第N+1..N+N行: 第 N+i行 包括一個(gè)正整數(shù): P_i輸出
* 第一行到第N行:第i行表示第i只奶牛需要被放慢的次數(shù)樣例輸入
51 4
5 4
1 3
2 4
4
2
1
5
3
樣例輸出
01
0
2
1
題目大意就是求每個(gè)點(diǎn)到根節(jié)點(diǎn)的鏈上有幾個(gè)點(diǎn)的點(diǎn)權(quán)(就是奶牛編號(hào))比這個(gè)點(diǎn)小。看其他人都是什么拿樹(shù)狀數(shù)組、樹(shù)鏈剖分、線段樹(shù)過(guò)的。最近寫(xiě)平衡樹(shù)比較爽的我就拿treap寫(xiě)了一下。首先求一條鏈(也就是一個(gè)數(shù)列)上比這個(gè)數(shù)小的數(shù)有多少個(gè),直接求一下當(dāng)前數(shù)在數(shù)列中的排名就好了,這個(gè)直接裸上treap。但因?yàn)橹豢紤]這條鏈上的點(diǎn),所以要在每次回溯到一個(gè)點(diǎn)時(shí)把這個(gè)點(diǎn)從treap中刪除。 最后附上代碼。 #include<cstdio> #include<cmath> #include<cstring> #include<algorithm> using namespace std; int n; int x,y; int tot; int root; int a[100010]; int s[100010]; int r[300010]; int v[300010]; int g[100010]; int to[200010]; int ls[300010]; int rs[300010]; int head[100010]; int next[200010]; int size[300010]; void add(int x,int y) {tot++;next[tot]=head[x];head[x]=tot;to[tot]=y; } void up(int x) {size[x]=size[rs[x]]+size[ls[x]]+1; } void rturn(int &x) {int t;t=ls[x];ls[x]=rs[t];rs[t]=x;size[t]=size[x];up(x);x=t; } void lturn(int &x) {int t;t=rs[x];rs[x]=ls[t];ls[t]=x;size[t]=size[x];up(x);x=t; } void insert_sum(int x,int &i) {if(!i){i=++tot;size[i]=1;v[i]=x;r[i]=rand();return ;}size[i]++;if(x>v[i]){insert_sum(x,rs[i]);if(r[rs[i]]<r[i]){lturn(i);}}else{insert_sum(x,ls[i]);if(r[ls[i]]<r[i]) {rturn(i);}}return ; } void delete_sum(int x,int &i) {if(i==0){return ;}if(v[i]==x){if((ls[i]*rs[i])==0){i=ls[i]+rs[i];}else if(r[ls[i]]<r[rs[i]]){rturn(i);delete_sum(x,i);}else{lturn(i);delete_sum(x,i);}return ;}size[i]--;if(v[i]<x){delete_sum(x,rs[i]);}else{delete_sum(x,ls[i]);}return ; } int ask_num(int x,int i) {if(i==0){return 0;}if(v[i]==x){return size[ls[i]]+1;}if(v[i]<x){return ask_num(x,rs[i])+size[ls[i]]+1;}return ask_num(x,ls[i]); } void dfs(int x,int fa) {for(int i=head[x];i;i=next[i]){if(to[i]!=fa){g[s[to[i]]]=ask_num(s[to[i]],root);insert_sum(s[to[i]],root);dfs(to[i],x);delete_sum(s[to[i]],root);}} } int main() {srand(12378);scanf("%d",&n);for(int i=1;i<n;i++){scanf("%d%d",&x,&y);add(x,y);add(y,x);}for(int i=1;i<=n;i++){scanf("%d",&a[i]);s[a[i]]=i;}insert_sum(s[1],root);g[s[1]]=0;dfs(1,1);for(int i=1;i<=n;i++){printf("%d\n",g[i]);} }
轉(zhuǎn)載于:https://www.cnblogs.com/Khada-Jhin/p/9147365.html
總結(jié)
以上是生活随笔為你收集整理的BZOJ1782[USACO 2010 Feb Gold 3.Slowing down]——dfs+treap的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: 前端基础(一):js数据类型
- 下一篇: 迟到两年,Lu1与Cee合作的经典单曲《