1. 程式人生 > >HDU1512 Monkey King

HDU1512 Monkey King

bsp 集合 兩個 clu define 維護 tdi names lan

題目來源HDU1512-Monkey King

這道題目題目大意就是,剛開始有N個猴子,他們有一個戰鬥力

他們互相並不認識

使他們認識的唯一條件就是兩個人幹一發打一架

他們中會有M次打架發生,如果兩個人互相認識了,他們就打不起來了,輸出-1,

如果兩個人不認識,那他們就會搞起來~兩個人在搞完後戰鬥力會減半

隨後兩個人就會認識,並且這道題目裏告訴我們朋友的朋友還是朋友~~~

輸出這個塊內戰鬥力最大是多少~~~

雖然我的解釋比較簡潔冗長,但是還是把題目大意說清楚了復雜了

這就是一道左偏樹的裸題嘛

我們用並查集維護兩個元素是否在同一個集合裏

因為左偏樹中已經存下了root,所以我們用起來就更爽了

雖然好簡單啊啊啊啊啊

但是手賤的我犯下了一個極大的錯誤

技術分享
  1 #include <cmath>
  2 #include <cstdio>
  3 #include <cstring>
  4 #include <iostream>
  5 #include <algorithm>
  6 #define ll long long
  7 #define fo(i,x,y) for(int i=x; i<=y; i++)
  8 #define pr(i,x,y) for(int i=x; i>=y; i--)
  9 #define clear(a,x) memset(a,x,sizeof(a))
 10
#define INF 1e9 11 #define EPS 1e-8 12 #define LiQin 1 > 0 13 14 using namespace std; 15 16 struct node 17 { 18 int l,r,d,w,root; 19 } tree[1000005]; 20 21 int N,M; 22 23 inline ll read() 24 { 25 int f=1; 26 ll Tmp=0; 27 char ch=getchar(); 28 while (ch !=
- && ch < 0 || ch > 9) 29 { 30 ch=getchar(); 31 } 32 if (ch == -) 33 { 34 f=-1; 35 ch=getchar(); 36 } 37 while (ch >= 0 && ch <= 9) 38 { 39 Tmp=Tmp * 10 + ch - 48; 40 ch=getchar(); 41 } 42 return Tmp * f; 43 } 44 45 int merge(int A,int B) 46 { 47 if (A == 0) 48 { 49 return B; 50 } 51 if (B == 0) 52 { 53 return A; 54 } 55 if (tree[A].w < tree[B].w) 56 { 57 swap(A,B); 58 } 59 tree[A].r=merge(tree[A].r,B); 60 tree[tree[A].r].root=A; 61 if (tree[tree[A].l].d < tree[tree[A].r].d) 62 { 63 swap(tree[tree[A].l].d , tree[tree[A].r].d);//相信大佬們已經看出來了,這裏交換的是左右兒子,而不是左右兒子的dist 64 } 65 if (tree[A].r) 66 { 67 tree[A].d=tree[tree[A].r].d + 1; 68 } 69 else 70 { 71 tree[A].d=0; 72 } 73 return A; 74 } 75 76 int pop(int u) 77 { 78 int L=tree[u].l; int R=tree[u].r; 79 tree[u].l=tree[u].r=tree[u].d=0; 80 tree[L].root=L; tree[R].root=R; 81 return merge(L,R); 82 } 83 84 int find1(int X) 85 { 86 if (tree[X].root != X) 87 { 88 return find1(tree[X].root); 89 } 90 else return X; 91 } 92 93 void solve(int u,int v) 94 { 95 int fx=find1(u); int fy=find1(v); 96 tree[fx].w/=2; tree[fy].w/=2; 97 int XXX=pop(fx); int YYY=pop(fy); 98 XXX=merge(XXX,fx); 99 YYY=merge(YYY,fy); 100 XXX=merge(XXX,YYY); 101 printf("%d\n",tree[XXX].w); 102 } 103 104 void Init() 105 { 106 fo(i,1,N) 107 { 108 tree[i].root=i; 109 tree[i].l=tree[i].r=tree[i].d=0; 110 } 111 } 112 113 int main() 114 { 115 while (scanf("%d",&N) == 1) 116 { 117 Init(); 118 fo(i,1,N) 119 { 120 tree[i].w=read(); 121 } 122 M=read(); 123 while (M--) 124 { 125 int u=read(); 126 int v=read(); 127 int fx=find1(u); 128 int fy=find1(v); 129 if (fx == fy) 130 { 131 printf("-1\n"); 132 } 133 else 134 { 135 solve(u,v); 136 } 137 } 138 } 139 }
View Code

好了好了

下面才是AC代碼

技術分享
  1 #include <cmath>
  2 #include <cstdio>
  3 #include <cstring>
  4 #include <iostream>
  5 #include <algorithm>
  6 #define ll long long
  7 #define fo(i,x,y) for(int i=x; i<=y; i++)
  8 #define pr(i,x,y) for(int i=x; i>=y; i--)
  9 #define clear(a,x) memset(a,x,sizeof(a))
 10 #define INF 1e9
 11 #define EPS 1e-8
 12 #define LiQin 1 > 0
 13 
 14 using namespace std;
 15 
 16 struct node
 17 {
 18     int l,r,d,w,root;    
 19 } tree[1000005];
 20 
 21 int N,M;
 22 
 23 inline ll read()
 24 { 
 25     int f=1;
 26     ll Tmp=0;
 27     char ch=getchar();
 28     while (ch != - && ch < 0 || ch > 9)
 29     {
 30         ch=getchar();
 31     }
 32     if (ch == -)
 33     {
 34         f=-1;
 35         ch=getchar();
 36     }
 37     while (ch >= 0 && ch <= 9)
 38     {
 39         Tmp=Tmp * 10 + ch - 48;
 40         ch=getchar();
 41     }
 42     return Tmp * f;
 43 }
 44 
 45 int merge(int A,int B)
 46 {
 47     if (A == 0)
 48     {
 49         return B;
 50     }
 51     if (B == 0)
 52     {
 53         return A;
 54     }
 55     if (tree[A].w < tree[B].w)
 56     {
 57         swap(A,B);
 58     }
 59     tree[A].r=merge(tree[A].r,B);
 60     tree[tree[A].r].root=A;
 61     if (tree[tree[A].l].d < tree[tree[A].r].d)
 62     {
 63         swap(tree[A].l , tree[A].r);
 64     }
 65     if (tree[A].r)
 66     {
 67         tree[A].d=tree[tree[A].r].d + 1;
 68     }
 69     else
 70     {
 71         tree[A].d=0;
 72     }
 73     return A;
 74 }
 75 
 76 int pop(int u)
 77 {
 78     int L=tree[u].l; int R=tree[u].r;
 79     tree[u].l=tree[u].r=tree[u].d=0;
 80     tree[L].root=L; tree[R].root=R;
 81     return merge(L,R);
 82 }
 83 
 84 int find1(int X)
 85 {
 86     if (tree[X].root != X) tree[X].root=find1(tree[X].root);
 87     return tree[X].root;
 88 }
 89 
 90 void solve(int u,int v)
 91 {
 92     int fx=find1(u); int fy=find1(v);
 93     tree[fx].w/=2; tree[fy].w/=2;
 94     int XXX=pop(fx); int YYY=pop(fy);
 95     XXX=merge(XXX,fx);
 96     YYY=merge(YYY,fy);
 97     XXX=merge(XXX,YYY);
 98     printf("%d\n",tree[XXX].w);
 99 }
100 
101 int main()
102 {
103     while (scanf("%d",&N) == 1)
104     {
105         fo(i,1,N)
106         {
107             tree[i].w=read();
108             tree[i].root=i;
109             tree[i].l=tree[i].r=tree[i].d=0;
110         }
111         M=read();
112         while (M--)
113         {
114             int u=read();
115             int v=read();
116             int fx=find1(u);
117             int fy=find1(v);
118             if (fx == fy)
119             {
120                 printf("-1\n");
121             }
122             else
123             {
124                 solve(u,v);
125             }
126         }
127     }
128 }
View Code

HDU1512 Monkey King