P4886 快递员
呃呃呃呃呃,兄弟们,终于AC快递员了,呃呃呃,这都什么日子啊,天天吃 18 发罚时。(来,兄弟们先吃)
思路
虽然有一堆点对,但是我们只用关注那些最长的点对即可,因为如果最长的点对已经不能放短了,那么你再怎么调其他的都改变不了现实,不过我们也要枚举每个点,所以时间还是很大,瓶颈在于会有很多不去要的冗余点,考虑直径最长,而直径上最为标志,最为好算的点就是重心,所以我们考虑每次跳重心,然后暴力算,那么一切将会分为一下几种情况:
- 当前最大的存在一条过重心,那么怎么动都会变得更大,直接输出
- 当前最大的边分布在了不同的重心的儿子子树中,那么同理动一次总有链被增加,所以也可以直接输出
- 以上都不满足,往最大边分布的儿子子树找重心然后跳即可
思路很简单,不过细节有点多
#include <iostream> #include <vector> using namespace std; const int MaxN = 2e5 + 10, MaxK = 19; struct S { int v, w; }; int dis[MaxN], sz[MaxN], bsz[MaxN], gt[MaxN], que[MaxN], a[MaxN], b[MaxN], qtg, root, ans = 1e9, tot, n, tn, m; vector<S> g[MaxN]; bool vis[MaxN]; void find(int x, int fa) { sz[x] = 1, bsz[x] = 0; for (auto i : g[x]) { if (vis[i.v] || i.v == fa) continue; find(i.v, x); sz[x] += sz[i.v]; bsz[x] = max(bsz[x], sz[i.v]); } bsz[x] = max(bsz[x], n - sz[x]); if (bsz[x] < bsz[root]) { root = x; } } void GOGOGO(int x, int rt, int fa = -1) { gt[x] = rt; for (auto i : g[x]) { if (i.v == fa) continue; dis[i.v] = dis[x] + i.w; GOGOGO(i.v, rt, x); } } void DFS(int x) { if (vis[x]) { cout << ans << endl; exit(0); } vis[x] = 1, dis[x] = 0; for (auto i : g[x]) { dis[i.v] = i.w, GOGOGO(i.v, i.v, x); } int mxl = 0; for (int i = 1, tmp; i <= m; i++) { tmp = dis[a[i]] + dis[b[i]]; if (mxl == tmp) que[++qtg] = i; if (mxl < tmp) { mxl = tmp, que[(qtg = 1)] = i; } } ans = min(ans, mxl); int lst = 0; for (int j = 1, tmp; j <= qtg; j++) { int i = que[j]; if (gt[a[i]] != gt[b[i]]) { cout << ans << endl; exit(0); } if (!lst) lst = gt[a[i]]; if (lst != gt[a[i]]) { cout << ans << endl; exit(0); } } root = 0, n = sz[lst], find(lst, 0), DFS(root); } signed main() { ios::sync_with_stdio(0), cin.tie(0); cin >> n >> m, tn = n; for (int i = 1, u, v, w; i < n; i++) { cin >> u >> v >> w; g[u].push_back({v, w}); g[v].push_back({u, w}); } for (int i = 1; i <= m; i++) { cin >> a[i] >> b[i]; } root = 0, bsz[0] = 1e9, find(1, 0), DFS(root); cout << ans << endl; return 0; }
本文作者:yabnto
本文链接:https://www.cnblogs.com/ybtarr/p/18403156
版权声明:本作品采用知识共享署名-非商业性使用-禁止演绎 2.5 中国大陆许可协议进行许可。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步