Avito Cool Challenge 2018 Solution
Posted dup4
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Avito Cool Challenge 2018 Solution相关的知识,希望对你有一定的参考价值。
A. Definite Game
签.
1 #include <bits/stdc++.h> 2 using namespace std; 3 4 int main() 5 { 6 int a; 7 while (scanf("%d", &a) != EOF) 8 { 9 [](int x) 10 { 11 for (int i = x - 1; i >= 1; --i) if (x % i) 12 { 13 printf("%d ", x - i); 14 return; 15 } 16 printf("%d ", x); 17 }(a); 18 } 19 return 0; 20 }
B. Farewell Party
签。
1 #include <bits/stdc++.h> 2 using namespace std; 3 4 #define N 100010 5 int n, a[N], b[N], cnt[N]; 6 vector <int> v[N]; 7 int ans[N]; 8 9 bool ok() 10 { 11 for (int i = 1; i <= n; ++i) if (!v[i].empty() && v[i].size() != i) 12 return false; 13 return true; 14 } 15 void solve() 16 { 17 int cnt = 0; 18 for (int i = 1; i <= n; ++i) v[i].clear(); 19 for (int i = 1; i <= n; ++i) 20 { 21 int id = n - a[i]; 22 if (v[id].size() == id) 23 { 24 ++cnt; 25 for (auto it : v[id]) ans[it] = cnt; 26 v[id].clear(); 27 } 28 v[id].push_back(i); 29 } 30 if (!ok()) 31 { 32 puts("Impossible"); 33 return; 34 } 35 else 36 { 37 for (int i = 1; i <= n; ++i) if (!v[i].empty()) 38 { 39 ++cnt; 40 for (auto it : v[i]) 41 ans[it] = cnt; 42 } 43 puts("Possible"); 44 for (int i = 1; i <= n; ++i) printf("%d%c", ans[i], " "[i == n]); 45 } 46 } 47 48 int main() 49 { 50 while (scanf("%d", &n) != EOF) 51 { 52 for (int i = 1; i <= n; ++i) scanf("%d", a + i); 53 solve(); 54 } 55 return 0; 56 }
D. Maximum Distance
Upsolved.
题意:
有一张图
定义一条路径的长度的路径上边权最大值
定义两点距离为两点之间最短路径
有一些特殊点,要对所有特殊点求离它最远的特殊点
思路:
我们考虑一条边所连接的两个连通块里,如果这两个连通块里都有特殊点
那么这条边的权值就可以用于更新特殊点的答案
其实就是一个求最小生成树的过程,先按边权排序
要注意的是不是求整个图的最小生成树,而是所有特殊点的最小生成树
其实是最小瓶颈生成树.
1 #include <bits/stdc++.h> 2 using namespace std; 3 4 #define N 100010 5 int n, m, k; 6 struct node 7 { 8 int u, v, w; 9 void scan() { scanf("%d%d%d", &u, &v, &w); } 10 bool operator < (const node &other) const { return w < other.w; } 11 }edge[N]; 12 13 int pre[N], cnt[N]; 14 int find(int x) { return pre[x] == 0 ? x : pre[x] = find(pre[x]); } 15 int Kruskal() 16 { 17 sort(edge + 1, edge + 1 + m); 18 for (int i = 1; i <= m; ++i) 19 { 20 int u = edge[i].u, v = edge[i].v, w = edge[i].w; 21 int fu = find(u), fv = find(v); 22 if (fu == fv) continue; 23 cnt[fv] += cnt[fu]; 24 pre[fu] = fv; 25 if (cnt[fv] == k) return w; 26 } 27 } 28 29 int main() 30 { 31 while (scanf("%d%d%d", &n, &m, &k) != EOF) 32 { 33 memset(pre, 0, sizeof pre); 34 memset(cnt, 0, sizeof cnt); 35 for (int i = 1, x; i <= k; ++i) scanf("%d", &x), cnt[x] = 1; 36 for (int i = 1; i <= m; ++i) edge[i].scan(); 37 int res = Kruskal(); 38 for (int i = 1; i <= k; ++i) printf("%d%c", res, " "[i == k]); 39 } 40 return 0; 41 }
以上是关于Avito Cool Challenge 2018 Solution的主要内容,如果未能解决你的问题,请参考以下文章
Avito Cool Challenge 2018 A. B题解
Avito Cool Challenge 2018:C. Colorful Bricks
Avito Cool Challenge 2018 B - Farewell Party
Avito Cool Challenge 2018:D. Maximum Distance (最小生成树)