June Challenge 2018 Division 2
Posted aguin
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了June Challenge 2018 Division 2相关的知识,希望对你有一定的参考价值。
暴力
1 #include <bits/stdc++.h> 2 using namespace std; 3 4 int main() { 5 int T; 6 scanf("%d", &T); 7 while(T--){ 8 int N, A, B, x, ca = 0, cb = 0; 9 scanf("%d %d %d", &N, &A, &B); 10 for(int i = 1; i <= N; ++i) { 11 scanf("%d", &x); 12 if(x == A) ca++; 13 if(x == B) cb++; 14 } 15 printf("%f ", 1.0 * ca * cb / N / N); 16 } 17 return 0; 18 }
每次可以加一个或者减到剩一个 特判几个点
1 #include <bits/stdc++.h> 2 using namespace std; 3 typedef long long LL; 4 5 int main() { 6 int T; 7 scanf("%d", &T); 8 while (T--) { 9 LL A, B, ca = 0, cb = 0; 10 scanf("%lld %lld", &A, &B); 11 if(A == B) {puts("0"); continue;} 12 if(B == 0) {puts("-1"); continue;} 13 B--; 14 for (int i = 0; i <= 62; ++i) { 15 if ((1LL << i) & A) ca++; 16 if ((1LL << i) & B) cb++; 17 } 18 if(B == 0) {puts(A == 0 ? "1" : "-1"); continue;} 19 if(ca == cb) puts("1"); 20 else if(ca > cb) puts("2"); 21 else printf("%d ", cb - ca + 1); 22 } 23 return 0; 24 }
二分 我连三维叉积都不会了
1 using namespace std; 2 const double eps = 1e-9; 3 4 double sqr(double x) {return x * x;} 5 double dis(double x1, double y1, double z1, double x2, double y2, double z2) { 6 return sqrt(sqr(x1 - x2) + sqr(y1 - y2) + sqr(z1 - z2)); 7 } 8 double cross(double x1, double y1, double z1, double x2, double y2, double z2) { 9 return sqrt(sqr(y1 * z2 - z1 * y2) + sqr(z1 * x2 - x1 * z2) + sqr(x1 * y2 - y1 * x2)); 10 } 11 12 int main() { 13 int T; 14 scanf("%d", &T); 15 while(T--) { 16 double Px, Py, Pz; 17 scanf("%lf %lf %lf", &Px, &Py, &Pz); 18 double Qx, Qy, Qz; 19 scanf("%lf %lf %lf", &Qx, &Qy, &Qz); 20 double dx, dy, dz; 21 scanf("%lf %lf %lf", &dx, &dy, &dz); 22 double cx, cy, cz, r; 23 scanf("%lf %lf %lf %lf", &cx, &cy, &cz, &r); 24 double ans = 1e10, tmp = 1e10; 25 while(tmp > eps) { 26 double M = ans - tmp; 27 double xx = Qx + dx * M; 28 double yy = Qy + dy * M; 29 double zz = Qz + dz * M; 30 double PQ = dis(Px, Py, Pz, xx, yy, zz); 31 double d = fabs(cross(Px - cx, Py - cy, Pz - cz, xx - cx, yy - cy, zz - cz)) / PQ; 32 if(d >= r) ans = M; 33 tmp /= 2; 34 } 35 printf("%.8f ", ans); 36 } 37 return 0; 38 }
字典树
1 #include <bits/stdc++.h> 2 using namespace std; 3 const int maxn = 1e6 + 10; 4 string S[maxn], P[maxn], ans[maxn]; 5 int R[maxn], id[maxn]; 6 char str[22]; 7 8 bool cmp(int i, int j) { 9 return R[i] < R[j]; 10 } 11 12 int cnt, nxt[maxn][26], val[maxn]; 13 void INS(int x) { 14 int u = 0; 15 for (int i = 0; i < S[x].length(); ++i) { 16 if (nxt[u][S[x][i] - ‘a‘]) u = nxt[u][S[x][i] - ‘a‘]; 17 else u = nxt[u][S[x][i] - ‘a‘] = ++cnt; 18 } 19 val[u] = 1; 20 } 21 string GET(int x) { 22 string ret = ""; 23 int u = 0, flag = 0; 24 for (int i = 0; i < P[x].length(); ++i) { 25 if (!flag && nxt[u][P[x][i] - ‘a‘]) ret += P[x][i], u = nxt[u][P[x][i] - ‘a‘]; 26 else { 27 if (val[u]) return ret; 28 flag = 1; 29 } 30 if (flag) 31 for (int j = 0; j < 26; ++j) { 32 if (nxt[u][j]) { 33 u = nxt[u][j]; 34 ret += ‘a‘ + j; 35 if (val[u]) return ret; 36 break; 37 } 38 } 39 } 40 if (val[u]) return ret; 41 while (1) { 42 for (int j = 0; j < 26; ++j) { 43 if (nxt[u][j]) { 44 u = nxt[u][j]; 45 ret += ‘a‘ + j; 46 if (val[u]) return ret; 47 break; 48 } 49 } 50 } 51 } 52 53 int main(){ 54 int N, Q; 55 scanf("%d", &N); 56 for(int i = 1; i <= N; ++i){ 57 scanf("%s", str); 58 S[i] = string(str); 59 } 60 scanf("%d", &Q); 61 for(int i = 1; i <= Q; ++i){ 62 scanf("%d %s", R + i, str); 63 P[i] = string(str); 64 id[i] = i; 65 } 66 sort(id + 1, id + 1 + Q, cmp); 67 int p = 0; 68 for(int i = 1; i <= Q; ++i) { 69 int x = id[i]; 70 while(p + 1 <= R[x]) INS(++p); 71 ans[x] = GET(x); 72 } 73 for(int i = 1; i <= Q; ++i) printf("%s ", ans[i].c_str()); 74 return 0; 75 }
枚举一个颜色的块 然后用并查集维护这个颜色以外的连通性 每条相邻边合并一次 所以是On的
1 #include <bits/stdc++.h> 2 using namespace std; 3 int ans, a[2222][2222], id[2222][2222]; 4 5 typedef pair<int, int> pii; 6 map< int, vector<pii> > M; 7 map< int, vector<pii> > :: iterator it; 8 9 int r[4444444]; 10 int fa[4444444]; 11 stack<pii> FA, R; 12 int Find(int x) { 13 return x == fa[x] ? x : Find(fa[x]); 14 } 15 void Union(int x, int y) { 16 x = Find(x), y = Find(y); 17 if(x == y) return; 18 if(r[x] < r[y]) swap(x, y); 19 FA.push(pii(y, fa[y])); 20 R.push(pii(x, r[x])); 21 fa[y] = x, r[x] += r[y]; 22 } 23 24 int dx[] = {1, 0, -1, 0}; 25 int dy[] = {0, 1, 0, -1}; 26 void dfs(int i, int j, int x) { 27 id[i][j] = x; 28 r[x]++; 29 ans = max(ans, r[x]); 30 for (int o = 0; o < 4; ++o) { 31 int nx = i + dx[o], ny = j + dy[o]; 32 if (a[nx][ny] == a[i][j] && !id[nx][ny]) dfs(nx, ny, x); 33 } 34 } 35 36 int cnt, cnt2, vis[2222][2222]; 37 map<int, int> mp; 38 void dfs1(int i, int j) { 39 vis[i][j] = 1; 40 for (int o = 0; o < 4; ++o) { 41 int nx = i + dx[o], ny = j + dy[o]; 42 if (a[nx][ny] && a[nx][ny] != a[i][j]) { 43 if (mp.find(a[nx][ny]) == mp.end()) 44 mp[a[nx][ny]] = ++cnt2 + cnt, fa[cnt + cnt2] = cnt + cnt2, r[cnt + cnt2] = r[id[i][j]]; 45 Union(id[nx][ny], mp[a[nx][ny]]); 46 ans = max(ans, r[Find(id[nx][ny])]); 47 } 48 if (a[nx][ny] == a[i][j] && !vis[nx][ny]) dfs1(nx, ny); 49 } 50 } 51 52 void cln(){ 53 while(!FA.empty()) { 54 pii x = FA.top(); FA.pop(); 55 fa[x.first] = x.second; 56 } 57 while(!R.empty()) { 58 pii x = R.top(); R.pop(); 59 r[x.first] = x.second; 60 } 61 } 62 63 int main() { 64 int n, m; 65 scanf("%d %d", &n, &m); 66 for(int i = 1; i <= n; ++i) 67 for(int j = 1; j <= m; ++j) 68 scanf("%d", &a[i][j]); 69 for(int i = 1; i <= n; ++i) { 70 for(int j = 1; j <= m; ++j) { 71 if(id[i][j]) continue; 72 dfs(i, j, ++cnt), fa[cnt] = cnt; 73 M[a[i][j]].push_back(pii(i, j)); 74 } 75 } 76 for(it = M.begin(); it != M.end(); it++) { 77 cnt2 = 0; 78 vector<pii> & v = (*it).second; 79 for(int i = 0; i < v.size(); ++i) { 80 int x = v[i].first, y = v[i].second; 81 mp.clear(), dfs1(x, y); 82 } 83 cln(); 84 } 85 printf("%d ", ans); 86 return 0; 87 }
考虑${d_i-i+1}$这个序列,每次可以加任意非负整数或者减一,枚举C的因子作为$d_{n}$然后倒着往前贪心,如果能+1就+1,否则减到最大的能整除的因子
1 #include <bits/stdc++.h> 2 using namespace std; 3 const int maxn = 1e6 + 10; 4 vector<int> fac, ans; 5 6 int main() { 7 int T; 8 scanf("%d", &T); 9 while(T--) { 10 int N, C; 11 scanf("%d %d", &N, &C); 12 fac.clear(); 13 for(int i = 1; i <= C / i; ++i) { 14 if(C % i == 0) { 15 fac.push_back(i); 16 if(i != C / i) fac.push_back(C / i); 17 } 18 } 19 sort(fac.begin(), fac.end()); 20 for(int i = 0; i < fac.size(); ++i) { 21 ans.clear(); 22 int cnt = 0, tmp = C; 23 for(int j = i; ; ) { 24 while (tmp % fac[j] != 0) j--; 25 tmp /= fac[j], cnt++, ans.push_back(fac[j]); 26 if(cnt == N || tmp == 1) break; 27 if(tmp % (fac[j] + 1) == 0) j++; 28 } 29 if(tmp == 1) break; 30 } 31 for(int i = ans.size() + 1; i <= N; ++i) ans.push_back(1); 32 for(int i = 0; i < N; ++i) printf("%d%c", ans[N-1-i] + i, i == N - 1 ? ‘ ‘ : ‘ ‘); 33 } 34 return 0; 35 }
只要求N段a的和,利用矩阵快速幂求前缀和减一下就可以了,又是向量乘……
1 #include <bits/stdc++.h> 2 using namespace std; 3 typedef long long LL; 4 const LL mod = 163577857; 5 int p[50005], a[105], c[105]; 6 int N, h, x, K; 7 8 struct Matrix { 9 LL a[105][105]; 10 void init() { 11 memset(a, 0, sizeof(a)); 12 for (int i = 0; i < 105; ++i) { 13 a[i][i] = 1; 14 } 15 } 16 } P[30]; 17 18 Matrix mul(Matrix a, Matrix b) { 19 Matrix ans; 20 memset(ans.a, 0, sizeof(ans.a)); 21 for (int i = 0; i < 105; ++i) { 22 for (int k = 0; k < 105; ++k) { 23 if (a.a[i][k] != 0) 24 for (int j = 0; j < 105; ++j) { 25 ans.a[i][j] = (ans.a[i][j] + a.a[i][k] * b.a[k][j]) % mod; 26 } 27 } 28 } 29 return ans; 30 } 31 32 LL sum[105], b[105], cpy[105]; 33 LL cal(int o) { 34 if(o <= K) return sum[o]; 35 o -= K; 36 for(int i = 1; i <= K; ++i) b[i] = a[1+K-i]; 37 b[K+1] = sum[K]; 38 for(int i = 0; i < 30; ++i) { 39 if(o & (1 << i)) { 40 memset(cpy, 0, sizeof(cpy)); 41 for(int j = 1; j <= K + 1; ++j) 42 for(int k = 1; k <= K + 1; ++k) 43 cpy[j] = (cpy[j] + P[i].a[j][k] * b[k]) % mod; 44 memcpy(b, cpy, sizeof(b)); 45 } 46 } 47 return b[K+1]; 48 } 49 50 LL fp(LL a, int b) { 51 LL ret = 1; 52 while (b) { 53 if (b & 1) ret = ret * a % mod; 54 a = a * a % mod; 55 b >>= 1; 56 } 57 return ret; 58 } 59 60 int main() { 61 scanf("%d %d %d %d", &N, &h, &x, &K); 62 for(int i = 1; i <= N; ++i) scanf("%d", p + i); 63 for(int i = 1; i <= K; ++i) scanf("%d", a + i), sum[i] = (sum[i-1] + a[i]) % mod; 64 for(int i = 1; i <= K; ++i) scanf("%d", c + i); 65 for(int i = 1; i <= K; ++i) P[0].a[1][i] = c[i]; 66 for(int i = 2; i <= K; ++i) P[0].a[i][i-1] = 1; 67 for(int i = 1; i <= K; ++i) P[0].a[K+1][i] = c[i]; 68 P[0].a[K+1][K+1] = 1; 69 for(int i = 1; i < 30; ++i) P[i] = mul(P[i-1], P[i-1]); 70 LL ans = 0; 71 for(int i = 1; i <= N; ++i) { 72 if(p[i] < x) ans = (ans + cal(p[i]) + cal(h) - cal(h - x + p[i]) + mod) % mod; 73 else ans = (ans + cal(p[i]) - cal(p[i] - x) + mod) % mod; 74 } 75 printf("%lld ", ans * fp(cal(h), mod - 2) % mod); 76 return 0; 77 }
以上是关于June Challenge 2018 Division 2的主要内容,如果未能解决你的问题,请参考以下文章
ZOJ Monthly, June 2018 - I District Division
Codeforces Avito Code Challenge 2018 D. Bookshelves
Codechef October Challenge 2018 游记
Avito Cool Challenge 2018 Solution