[NOIP2014]
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
1 #include <stdio.h> 2 using namespace std; 3 int a[300],b[300],n,na,nb,tot1=0,tot2=0,ans1=0,ans2=0; 4 int f[5][5]={0,0,1,1,0,1,0,0,1,0,0,1,0,0,1,0,0,1,0,1,1,1,0,0,0}; 5 int main() 6 { 7 scanf("%d %d %d", &n, &na, &nb); 8 for (int i=0;i<na;i++) 9 scanf("%d", &a[i]); 10 for (int i=0;i<nb;i++) 11 scanf("%d", &b[i]); 12 for (int i=1;i<=n;i++) 13 { 14 tot1+=f[a[ans1]][b[ans2]]; 15 tot2+=f[b[ans2]][a[ans1]]; 16 ans1++; if (ans1==na) ans1=0; 17 ans2++; if (ans2==nb) ans2=0; 18 } 19 printf("%d %d", tot1,tot2); 20 return 0; 21 }
2.联合权值
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
1 #include <stdio.h> 2 #include <string.h> 3 #include <queue> 4 #include <algorithm> 5 using namespace std; 6 struct node 7 { 8 int u, v, sum, max, next; 9 }a[400020]; 10 int vis[200020], dis[200020], w[200020], tot, n, maxx; 11 int first[400020], head, tail, q[400020]; 12 long long ans; 13 void addedge(int u, int v) 14 { 15 a[++tot].u = u; 16 a[tot].v = v; 17 a[tot].next = first[u]; 18 first[u] = tot; 19 } 20 int bfs1() 21 { 22 q[0] = 1; 23 vis[1] = 1; 24 dis[1] =1; 25 tail = 1; 26 head = 0; 27 while (head != tail) 28 { 29 int u = q[head++]; 30 for (int e = first[u]; e != -1; e = a[e].next) 31 { 32 int v = a[e].v; 33 if (!vis[v]) 34 { 35 if (w[v] > a[u].max)a[u].max = w[v]; 36 dis[v] = dis[u] + 1; 37 a[u].sum = (a[u].sum + w[v]) % 10007; 38 vis[v] = 1; 39 q[tail++] = v; 40 } 41 } 42 } 43 return 0; 44 } 45 int bfs2() 46 { 47 q[0] = 1; 48 vis[1] =1; 49 tail = 1; 50 head = 0; 51 while (head != tail) 52 { 53 int u = q[head++]; 54 int maxb = 0; 55 long long tmp = 0; 56 for (int e = first[u]; e != -1; e = a[e].next) 57 { 58 int v = a[e].v; 59 if (!vis[v]&&dis[v] == dis[u] + 1) 60 { 61 ans += (tmp * w[v]); 62 ans = ans % 10007; 63 if (maxb * w[v] > maxx)maxx = maxb * w[v]; 64 tmp += w[v]; 65 tmp = tmp % 10007; 66 ans += (w[u] * a[v].sum); 67 ans = ans % 10007; 68 if (w[u]*a[v].max > maxx)maxx = w[u]*a[v].max; 69 vis[v] = 1; 70 q[tail++] = v; 71 if (w[v] > maxb)maxb = w[v]; 72 } 73 } 74 } 75 return 0; 76 } 77 int main() 78 { 79 int x, y; 80 memset(first, -1, sizeof(first)); 81 scanf("%d", &n); 82 for (int i = 1; i < n; i++) 83 { 84 scanf("%d%d", &x, &y); 85 addedge(x, y); 86 addedge(y, x); 87 } 88 for (int j = 1; j <= n; j++) 89 scanf("%d", &w[j]); 90 bfs1(); 91 memset(vis, 0, sizeof(vis)); 92 bfs2(); 93 printf("%d ", maxx); 94 printf("%lld\n", (ans*2)%10007); 95 }
3.飞扬的小鸟
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
#include <stdio.h> #include <algorithm> #define maxn 10005 using namespace std; struct node { int l, h; }a[maxn]; int n, m, k, x[maxn], y[maxn], f[maxn][1005], ans, u, v, w; int main() { scanf("%d %d %d", &n, &m, &k); for (int i = 1; i <= n; i++) { scanf("%d %d", &x[i], &y[i]); } for (int i = 1; i <= k; i++) { scanf("%d %d %d", &u, &v, &w); a[u].l = v;a[u].h = w; } for (int i = 1; i <= n; i++) for (int j = 1; j <= m; j++)f[i][j] = 2000000000; for (int i = 1; i <= n; i++) { for (int j = 1; j <= m; j++) { int t = min(m, j + x[i]); f[i][t] = min(f[i-1][j]+1, f[i][t]); f[i][t] = min(f[i][j]+1, f[i][t]); //if (x[i]) // for(int k = 1; k <= (m-j)/x[i]; k++) // if(j-k*x[i]>0)f[i][j] = min(f[i-1][j - k*x[i]]+k, f[i-1][j] + k); } for (int j = y[i] + 1; j <= m; j++) { f[i][j-y[i]] = min(f[i-1][j], f[i][j-y[i]]); } if (a[i].h!=0) for (int j = a[i].h; j <= m; j++)f[i][j] = 2000000000; if (a[i].l!=0) for (int j = 0; j <= a[i].l; j++)f[i][j] = 2000000000; } ans = 2000000000; for (int i = 1; i <= m; i++) ans = min(ans, f[n][i]); if (ans < 2000000000) printf("1\n%d\n", ans); else if(ans = 2000000000) { ans = 0; for (int i = 1; i <= n; i++) { if (a[i].l||a[i].h) { int flag = 0; for (int j = a[i].l; j < a[i].h; j++) if (f[i][j] < 2000000000)flag = 1; if (flag)ans++; else break; } } printf("0\n%d\n", ans); } }
4.无线网络发射选址
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
#include <stdio.h> int d, n, f[500][500], ans, x, y, k, tot; int find(int x, int y) { int tmp = 0, x1, y1, x0, y0; x0 = x-d;y0 = y-d; x1 = x + d;y1 = y + d; if (x1 > 128)x1 = 128; if (y1 > 128)y1 = 128; if(x0 < 0) x0 = 0; if(y0 < 0) y0 = 0; for (int i = x0; i <= x1; i++) for (int j = y0; j <= y1; j++) { if(f[i][j]){tmp += f[i][j];} } return tmp; } int main() { scanf("%d", &d); scanf("%d", &n); for (int i = 1; i <= n; i++) { scanf("%d %d %d", &x, &y, &k); f[x][y] = k; } for (int i = 0; i <= 128; i++) for (int j = 0; j <= 128; j++) { int l = find(i ,j); if (l > ans){ans = l;} } for (int i = 0; i <= 128; i++) for (int j = 0; j <= 128; j++) { int l = find(i ,j); if (l == ans){tot++;} } printf("%d ", tot); printf("%d\n", ans); }
5.寻找道路
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
#include <algorithm> #define maxn 200010 using namespace std; int q[maxn], n, m, tot, vi[maxn], vis[maxn], fa[maxn], first[maxn], first1[maxn]; int done[maxn], cnt, dis[maxn], s, t, x, y, Q[maxn], S, viss[maxn]; struct node { int u, v, next; }a[maxn], b[maxn]; void addedge(int st, int end) { a[++tot].u = st; a[tot].v = end; a[tot].next = first[st]; first[st] = tot; } void addedge1(int st, int end) { b[++cnt].u = st; b[cnt].v = end; b[cnt].next = first1[st]; first1[st] = cnt; } int bfs() { q[0] = t; vi[t] = 1; int head = 0,tail = 1; while (head != tail) { int u = q[head++]; for (int e = first[u]; e != -1; e = a[e].next) { int v = a[e].v; if (!vi[v]){ vi[v] = 1; q[tail++] = v; } } } q[0] = S; head = 0,tail = 1; //viss[S] = 1; while (head != tail) { int u = q[head++]; if (viss[u]) continue; viss[u] = 1; for (int e = first1[u]; e != -1; e = b[e].next) { int v = b[e].v; if (!vi[v]) { vi[u] = 2; } q[++tail] = v; } } return 0; } int dij() { for (int i = 1; i <= n; i++)dis[i] = 2000000000; Q[0] = S; dis[S] = 0; int head = 0, tail = 1; while (head != tail) { int u = Q[head++]; if (done[u]) continue; done[u] = 1; for (int e = first1[u]; e != -1; e = b[e].next) { int v = b[e].v; if (vi[v] == 1) if (dis[u]+1 < dis[v]) { dis[v] = dis[u] + 1; Q[tail++] = v; } } } return dis[t]; } int main() { scanf("%d %d", &n, &m); memset(first1, -1, sizeof(first1)); memset(first, -1, sizeof(first)); for (int i = 1; i <= m; i++) { scanf("%d %d", &x, &y); addedge(y, x); addedge1(x, y); // fa[y] = x; } scanf("%d %d", &S, &t); bfs(); int flag = dij(); if (flag < 2000000000) printf("%d\n",flag); else printf("-1\n"); }
6.解方程
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
int prime[5] = {11261,19997,22877,21893,14843}, len; int pre[5][1000010], an[1000010]; char s[1010000]; int main() { scanf("%d %d", &n, &m); for(int i = 0; i <= n; i++) { int flag = 1, tmp; scanf("%s", s+1); len = strlen(s+1); for (int t = 0; t < 5; t++) { tmp = 0; for (int j = 1; j <= len; j++) { if (s[j] == '-'){flag = -1;continue;} tmp = (tmp*10 + (s[j] - '0'))%prime[t]; } a[t][i] = flag * tmp; } } for (int t = 0; t < 5; t++) for (int i = 0; i < prime[t]; i++) { int v = a[t][n]; for (int j = n-1; j >= 0; j--) { v = (a[t][j] + v*i) % prime[t]; } if (v == 0)pre[t][i] = 1; } for (int t = 0; t < 5; t++) for (int i = 0; i <= m; i++) { if (pre[t][i%prime[t]])ans[t][i] = 1; } for (int i = 1; i <= m; i++) { int u = 0; for(int t = 0; t < 5; t++) { if (ans[t][i])u++; } if(u == 5)an[++tot] = i; } printf("%d\n", tot); for (int i = 1; i <= tot; i++) printf("%d\n", an[i]); }