hdu5353
模拟,,,
每个人有一些糖果,每两个人之间只能给一个糖果,问最后是否能让所有人的糖果数量相同,只要确定一个糖果的流向其他的就能够确定。
马虎了,卡了好几天,心塞塞的。。。
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
#include<iostream> #include<string.h> #include<stdio.h> using namespace std; const int maxa = 100005; int biaoji[maxa]; int vis[maxa]; int put[maxa][2]; int ans(int a[], int n){ int sta; int o = 0; for(int i =0;i < n; i++){ if(a[i] > 0){ sta = i; break; } } memset(vis, 0, sizeof(vis)); int len = 0; int last = 0; for(int k = sta;; k++){ if(len++ > n*3) break; int i = k % n; if(vis[i] == 1){ last = 0; continue; } if(last == 1 && a[i] == 1){ last = 0; continue; } if(a[i] > 0){ last = 0; put[o][0] = i; put[o++][1] = (i+1)%n; vis[i] = 1; a[i] --, a[(i+1)%n] ++; }else if(a[i] < 0) last = 1; } /*for(int i =0 ;i < n; i++){ printf("%d ", a[i]); }puts("");*/ len = 0; last = 0; for(int i = sta; ; i--){ i = (i%n+n*800)%n; if(len++ > n*3) break; if(vis[(i+n-1)%n] == 1)continue; if(a[i] > 0){ put[o][0] = i; put[o++][1] = (i+n-1)%n; vis[(i+n-1)%n] = 1; a[i] --; a[(i-1+n)%n] ++; } } for(int i = 0;i < n; i++){ if(a[i] != 0) return 0; } puts("YES"); printf("%d\n", o); for(int i = 0;i < o; i++){ printf("%d %d\n", put[i][0]+1, put[i][1]+1); }return 1; } int ans1(int a[], int n){ int sta; int o = 0; for(int i =0;i < n; i++){ if(a[i] > 0){ sta = i; break; } } memset(vis, 0, sizeof(vis)); int len = 0; int last = 0; for(int i = sta; ; i--){ i = (i%n+n)%n; if(last == 1 && a[i] == 1){ last = 0; continue; } if(len++ > n*3) break; if(vis[(i+n-1)%n] == 1){ last = 0; continue; } if(a[i] > 0){ put[o][0] = i; put[o++][1] = (i+n-1)%n; vis[(i+n-1)%n] = 1; a[i] --; a[(i-1+n)%n] ++; }else if(a[i] < 0){ last = 1; } } /*for(int i =0 ;i < n; i++){ printf("%d ", a[i]); }puts("");*/ len = 0; last = 0; for(int k = sta;; k++){ if(len++ > n*3) break; int i = k % n; if(vis[i] == 1)continue;; if(a[i] > 0){ last = 0; put[o][0] = i; put[o++][1] = (i+1)%n; vis[i] = 1; a[i] --, a[(i+1)%n] ++; } } for(int i = 0;i < n; i++){ if(a[i] != 0) return 0; } puts("YES"); printf("%d\n", o); for(int i = 0;i < o; i++){ printf("%d %d\n", put[i][0]+1, put[i][1]+1); }return 1; } int a[maxa], b[maxa], c[maxa]; int main(){ int t; scanf("%d", &t); while(t--){ memset(biaoji, 0, sizeof(biaoji)); int n; scanf("%d", &n); long long sum = 0; int ok = 0; for(int i = 0;i < n; i++){ scanf("%d", &a[i]); sum += a[i]; } for(int i = 1; i < n; i++){ if(a[i] != a[i-1]){ ok = 1; break; } } int ook = 0; for(int i = 0;i < n; i++){ b[i] = a[i] - sum/n; c[i] = b[i]; if(c[i] > 1)biaoji[i] = 1; else biaoji[i] = 0; if(b[i] > 2 || b[i] < -2) ook =1; } if(ok == 0){ puts("YES\n0"); continue; } if(sum % n != 0 || ook){ puts("NO"); continue; } if(ans(b, n)); else if(ans1(c, n)); else puts("NO"); } } /* 5 6 2 0 0 2 0 2 8 3 0 0 3 0 2 0 0 8 3 0 0 3 0 0 2 0 8 0 0 3 3 0 0 2 0 8 1000000000 1000000000 1000000000 1000000000 1000000000 1000000000 1000000000 1000000001 */
这是a过后花了二十分钟敲的不那么丑但依旧很丑的代码
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
#include<iostream> #include<stdio.h> #include<string.h> using namespace std; const int maxa = 100005; int put[maxa][2], vis[maxa]; int ans(int n, int a[]){ int sta= 0; for(int i = 0;i < n; i++){ if(a[i] > 0){ sta = i; } } memset(vis, 0, sizeof(vis)); int len = 0, last = 0, o =0 ; for(int i = sta; ;i++){ i = i%n; if(len++ > 3*n) break; if(vis[i] == 1){ last= 0; continue; } if(last == 1 && a[i] == 1){ last = 0; continue; } if(a[i] > 0){ vis[i] = 1; a[i] --, a[(i+1)%n] ++; put[o][0] = i; put[o][1] = (i+1)%n; o++; }else if(a[i] < 0){ last = 1; } } len = 0, last = 0; for(int i = sta; ; i--){ i = (i+n)%n; if(len++ > n*3) break; if(vis[(i+n-1)%n] == 1){ last = 0; continue;; } if(last == 1 && a[i] == 1){ last = 0; continue; } if(a[i] > 0){ vis[(i+n-1)%n] = 1; a[i] --, a[(i+n-1)%n] ++; put[o][0] = i; put[o][1] = (i+n-1)%n; o++; }else if(a[i] < 0) last = 1; } for(int i =0 ; i< n; i++){ if(a[i]) return 0; } puts("YES"); printf("%d\n", o); for(int i = 0 ;i < o; i++){ printf("%d %d\n", 1+put[i][0], 1+put[i][1]); } return 1; } int ans1(int n, int a[]){ int sta= 0; for(int i = 0;i < n; i++){ if(a[i] > 0){ sta = i; } } memset(vis, 0, sizeof(vis)); int len = 0, last = 0, o =0 ; for(int i = sta; ; i--){ i = (i+n)%n; if(len++ > n*3) break; if(vis[(i+n-1)%n] == 1){ last = 0; continue;; } if(last == 1 && a[i] == 1){ last = 0; continue; } if(a[i] > 0){ vis[(i+n-1)%n] = 1; a[i] --, a[(i+n-1)%n] ++; put[o][0] = i; put[o][1] = (i+n-1)%n; o++; }else if(a[i] < 0) last = 1; } len = 0, last = 0; for(int i = sta; ;i++){ i = i%n; if(len++ > 3*n) break; if(vis[i] == 1){ last= 0;;continue; } if(last == 1 && a[i] == 1){ last = 0; continue; } if(a[i] > 0){ vis[i] = 1; a[i] --, a[(i+1)%n] ++; put[o][0] = i; put[o][1] = (i+1)%n; o++; }else if(a[i] < 0){ last = 1; } } for(int i =0 ; i< n; i++){ if(a[i]) return 0; } puts("YES"); printf("%d\n", o); for(int i = 0 ;i < o; i++){ printf("%d %d\n", 1+put[i][0], 1+put[i][1]); } return 1; } int a[maxa], b[maxa], c[maxa]; int main(){ int n, t; scanf("%d", &t); while(t--){ scanf("%d", &n); long long sum = 0; for(int i = 0;i < n; i++){ scanf("%d", &a[i]); sum += a[i]; } if(sum % n){ puts("NO"); continue; } for(int i = 0;i < n; i++){ b[i] = a[i] - sum /n; c[i] = b[i]; } if(ans(n, b)) ; else if(ans1(n, c)); else puts("NO"); } }