codeforces #294 div2 only

2015-03-01 00:23:47

总结:A,B,C水题,D题翔提示哒,E题是个LCA加分类讨论,比赛中没敲完。。。

  比赛搞了4题,赛后补了E。小结一下...(Orz Jay巨一小时AK...)

A:暴力,注意Knight的符号是'n'(Jay巨这里逗比辣..)

 1 #include <cstdio>
 2 #include <cstring>
 3 #include <cstdlib>
 4 #include <cmath>
 5 #include <vector>
 6 #include <map>
 7 #include <set>
 8 #include <stack>
 9 #include <queue>
10 #include <string>
11 #include <iostream>
12 #include <algorithm>
13 using namespace std;
14 
15 #define MEM(a,b) memset(a,b,sizeof(a))
16 #define REP(i,n) for(int i=1;i<=(n);++i)
17 #define REV(i,n) for(int i=(n);i>=1;--i)
18 #define FOR(i,a,b) for(int i=(a);i<=(b);++i)
19 #define RFOR(i,a,b) for(int i=(a);i>=(b);--i)
20 #define getmid(l,r) ((l) + ((r) - (l)) / 2)
21 #define MP(a,b) make_pair(a,b)
22 
23 typedef long long ll;
24 typedef pair<int,int> pii;
25 const int INF = (1 << 30) - 1;
26 
27 char g[10][10];
28 
29 int main(){
30     for(int i = 0; i < 8; ++i)
31         scanf("%s",g[i]);
32     int a1 = 0,a2 = 0;
33     for(int i = 0; i < 8; ++i){
34         for(int j = 0; j < 8; ++j){
35             char c = g[i][j];
36             if(c == 'Q') a1 += 9;
37             else if(c == 'R') a1 += 5;
38             else if(c == 'B' || c == 'N') a1 += 3;
39             else if(c == 'P') a1 += 1;
40             else if(c == 'q') a2 += 9;
41             else if(c == 'r') a2 += 5;
42             else if(c == 'b' || c == 'n') a2 += 3;
43             else if(c == 'p') a2 += 1;
44         }
45     }
46     if(a1 == a2) printf("Draw\n");
47     else if(a1 > a2) printf("White\n");
48     else printf("Black\n");
49     return 0;
50 }
View Code

 

B:暴力,排序。

 1 #include <cstdio>
 2 #include <cstring>
 3 #include <cstdlib>
 4 #include <cmath>
 5 #include <vector>
 6 #include <map>
 7 #include <set>
 8 #include <stack>
 9 #include <queue>
10 #include <string>
11 #include <iostream>
12 #include <algorithm>
13 using namespace std;
14 
15 #define MEM(a,b) memset(a,b,sizeof(a))
16 #define REP(i,n) for(int i=1;i<=(n);++i)
17 #define REV(i,n) for(int i=(n);i>=1;--i)
18 #define FOR(i,a,b) for(int i=(a);i<=(b);++i)
19 #define RFOR(i,a,b) for(int i=(a);i>=(b);--i)
20 #define getmid(l,r) ((l) + ((r) - (l)) / 2)
21 #define MP(a,b) make_pair(a,b)
22 
23 typedef long long ll;
24 typedef pair<int,int> pii;
25 const int INF = (1 << 30) - 1;
26 
27 int n;
28 int a[100010],b[100010],c[100010];
29 
30 int main(){
31     scanf("%d",&n);
32     REP(i,n) scanf("%d",a + i);
33     REP(i,n - 1) scanf("%d",b + i);
34     REP(i,n - 2) scanf("%d",c + i);
35     sort(a + 1,a + n + 1);
36     sort(b + 1,b + n);
37     sort(c + 1,c + n - 1);
38     REP(i,n) if(a[i] != b[i]){
39         printf("%d\n",a[i]);
40         break;
41     }
42     REP(i,n - 1) if(b[i] != c[i]){
43         printf("%d\n",b[i]);
44         break;
45     }
46     return 0;
47 }
View Code

 

C:暴力扫,找答案即可。用公式min(a,b,(a+b)/3))也行。

 1 #include <cstdio>
 2 #include <cstring>
 3 #include <cstdlib>
 4 #include <cmath>
 5 #include <vector>
 6 #include <map>
 7 #include <set>
 8 #include <stack>
 9 #include <queue>
10 #include <string>
11 #include <iostream>
12 #include <algorithm>
13 using namespace std;
14 
15 #define MEM(a,b) memset(a,b,sizeof(a))
16 #define REP(i,n) for(int i=1;i<=(n);++i)
17 #define REV(i,n) for(int i=(n);i>=1;--i)
18 #define FOR(i,a,b) for(int i=(a);i<=(b);++i)
19 #define RFOR(i,a,b) for(int i=(a);i>=(b);--i)
20 #define getmid(l,r) ((l) + ((r) - (l)) / 2)
21 #define MP(a,b) make_pair(a,b)
22 
23 typedef long long ll;
24 typedef pair<int,int> pii;
25 const int INF = (1 << 30) - 1;
26 
27 int n,m;
28 
29 int main(){
30     scanf("%d%d",&n,&m);
31     int ans = 0;
32     for(int i = 0; i <= m; ++i){
33         int tn = n - 2 * i;
34         if(tn < 0) break;
35         int tm = m - i;
36         ans = max(ans,i + min(tn,tm / 2));
37     }
38     printf("%d\n",ans);
39     return 0;
40 }
View Code

 

D:维护前缀和,用map[i][j]表示以i字符结尾,前缀和为j的情况数。具体代码可见。

 1 #include <cstdio>
 2 #include <cstring>
 3 #include <cstdlib>
 4 #include <cmath>
 5 #include <vector>
 6 #include <map>
 7 #include <set>
 8 #include <stack>
 9 #include <queue>
10 #include <string>
11 #include <iostream>
12 #include <algorithm>
13 using namespace std;
14 
15 #define MEM(a,b) memset(a,b,sizeof(a))
16 #define REP(i,n) for(int i=1;i<=(n);++i)
17 #define REV(i,n) for(int i=(n);i>=1;--i)
18 #define FOR(i,a,b) for(int i=(a);i<=(b);++i)
19 #define RFOR(i,a,b) for(int i=(a);i>=(b);--i)
20 #define getmid(l,r) ((l) + ((r) - (l)) / 2)
21 #define MP(a,b) make_pair(a,b)
22 
23 typedef long long ll;
24 typedef pair<int,int> pii;
25 const int INF = (1 << 30) - 1;
26 
27 int v[30];
28 map<ll,int> mp[30];
29 char s[100010];
30 
31 int main(){
32     for(int i = 0; i < 26; ++i) scanf("%d",v + i);
33     ll ans = 0,sum = 0;
34     scanf("%s",s + 1);
35     int len = strlen(s + 1);
36     REP(i,len){
37         int id = s[i] - 'a';
38         ans += mp[id][sum];
39         sum += v[id];
40         mp[id][sum]++;
41     }
42     printf("%I64d\n",ans);
43     return 0;
44 }
View Code

 

E:求出树中距离两点距离相等的点的个数。首先倍增求两个点a,b的lca,然后分3类讨论。

(1)lca == a 或者 lca == b,求出a,b的中点,如果没有中点答案是0,否则从中点延伸出去的子树都符合。

(2)lca != a ,lca != b,且a到lca的距离等于b到lca的距离.....

(3)lca != a, lca != b,且a到lca的距离不等于b到lca的距离.....

  1 #include <cstdio>
  2 #include <cstring>
  3 #include <cstdlib>
  4 #include <cmath>
  5 #include <vector>
  6 #include <map>
  7 #include <set>
  8 #include <stack>
  9 #include <queue>
 10 #include <string>
 11 #include <iostream>
 12 #include <algorithm>
 13 using namespace std;
 14 
 15 #define MEM(a,b) memset(a,b,sizeof(a))
 16 #define REP(i,n) for(int i=1;i<=(n);++i)
 17 #define REV(i,n) for(int i=(n);i>=1;--i)
 18 #define FOR(i,a,b) for(int i=(a);i<=(b);++i)
 19 #define RFOR(i,a,b) for(int i=(a);i>=(b);--i)
 20 #define getmid(l,r) ((l) + ((r) - (l)) / 2)
 21 #define MP(a,b) make_pair(a,b)
 22 
 23 typedef long long ll;
 24 typedef pair<int,int> pii;
 25 const int INF = (1 << 30) - 1;
 26 const int MAXN = 100010;
 27 const int MAX_LOG = 20;
 28 
 29 int n,m;
 30 int first[MAXN],ecnt;
 31 int fa[MAX_LOG][MAXN],dep[MAXN];
 32 int dis[MAXN],sz[MAXN];
 33 
 34 struct edge{
 35     int v,next;
 36 }e[MAXN << 1];
 37 
 38 void Init(){
 39     MEM(first,-1);
 40     ecnt = 0;
 41 }
 42 
 43 void Add_edge(int u,int v){
 44     e[++ecnt].next = first[u];
 45     e[ecnt].v = v;
 46     first[u] = ecnt;
 47 }
 48 
 49 void Dfs(int p,int pre,int d){
 50     fa[0][p] = pre;
 51     dep[p] = d;
 52     sz[p] = 1;
 53     for(int i = first[p]; ~i; i = e[i].next){
 54         int v = e[i].v;
 55         if(v == pre) continue;
 56         Dfs(v,p,d + 1);
 57         sz[p] += sz[v];
 58     }
 59 }
 60 
 61 void Pre(){
 62     Dfs(1,-1,0);
 63     for(int k = 0; k + 1 < MAX_LOG; ++k){
 64         for(int v = 1; v <= n; ++v){
 65             if(fa[k][v] < 0) fa[k + 1][v] = -1;
 66             else fa[k + 1][v] = fa[k][fa[k][v]];
 67         }
 68     }
 69 }
 70 
 71 int Lca(int u,int v){
 72     if(dep[u] > dep[v]) swap(u,v);
 73     for(int k = MAX_LOG - 1; k >= 0; --k){
 74         if((dep[v] - dep[u]) & (1 << k))
 75             v = fa[k][v];
 76     }
 77     if(u == v) return u;
 78     for(int k = MAX_LOG - 1; k >= 0; --k){
 79         if(fa[k][u] != fa[k][v]){
 80             u = fa[k][u];
 81             v = fa[k][v];
 82         }
 83     }
 84     return fa[0][u];
 85 }
 86 
 87 int Up(int d,int u){
 88     for(int k = MAX_LOG - 1; k >= 0; --k){
 89         if(d & (1 << k))
 90             u = fa[k][u];
 91     }
 92     return u;
 93 }
 94 
 95 int Solve(int a,int b){
 96     int lca = Lca(a,b);
 97     //printf("lca : %d\n",lca);
 98     if(lca == a || lca == b){
 99         int d = abs(dep[a] - dep[b]);
100         if(dep[a] > dep[b]) swap(a,b);
101         if(d % 2 == 0){
102             d /= 2;
103             b = Up(d - 1,b);
104             int bf = fa[0][b];
105             return sz[bf] - sz[b];
106         }
107         else return 0;
108     }
109     else{
110         int d = dep[a] - dep[lca] + dep[b] - dep[lca];
111         if(d % 2 == 0){
112             d /= 2;
113             if(dep[a] - dep[lca] == dep[b] - dep[lca])
114                 return n - sz[Up(d - 1,a)] - sz[Up(d - 1,b)];
115             else{
116                 if(dep[a] > dep[b]) swap(a,b);
117                 b = Up(d - 1,b);
118                 int bf = fa[0][b];
119                 return sz[bf] - sz[b];
120             }
121         }
122         else return 0;
123     }
124 }
125 
126 int main(){
127     Init();
128     int a,b;
129     scanf("%d",&n);
130     REP(i,n - 1){
131         scanf("%d%d",&a,&b);
132         Add_edge(a,b);
133         Add_edge(b,a);
134     }
135     Pre();
136     scanf("%d",&m);
137     REP(i,m){
138         scanf("%d%d",&a,&b);
139         if(a == b) printf("%d\n",n);
140         else printf("%d\n",Solve(a,b));
141     }
142     return 0;
143 }
View Code

 

posted @ 2015-03-01 01:00  Naturain  阅读(115)  评论(0编辑  收藏  举报