换根DP
换根DP
无根树上的DP?
相关资料
第一个例题距离和
洛谷类似题 - 洛谷 P3478 [POI2008] STA-Station
有一棵
朴素的思想就是枚举每个点作为根遍历整棵树,那么
定义两个数组 f 和 v:
那么第一次 dfs 时可以维护数组 f 的值,
第二次 dfs 可以维护数组 v 的值,
未验证的代码
int n, sz[N], f[N], v[N]; vector<int> e[N]; /* f[i] 表示以节点 i 为根的子树中的点到 i 的距离和 v[i] 表示把节点 i 的父亲 x 作为节点 i 的孩子节点时以 x 为根的子树中的点到 i 的距离和 */ void dfs1(int u, int fa){ sz[u] = 1; f[u] = 0; for(auto v : e[u]){ if(v == fa) continue; dfs1(v, u); sz[u] += sz[v]; f[u] += f[v]; } f[u] += sz[u] - 1; return ; } void dfs2(int u, int fa){ for(auto t : e[u]){ if(t == fa) continue; v[t] = v[u] + f[u] - f[t] - sz[t] + n - sz[t]; dfs2(t, u); } return ; } void solve(){ cin >> n; for(int i = 1; i < n; ++ i){ int u, v; cin >> u >> v; e[u].push_back(v); e[v].push_back(u); } dfs1(1, 0); dfs2(1, 0); for(int i = 1; i <= n; ++ i){ cout << f[i] + v[i] << '\n'; } return ; }
第二个例题 流
依旧是考虑以节点 x 为根的子树可以承担的最大流量,以及将节点 x 的父节点作为子节点时可以承担的最大流量,此问题还得考虑边对转移的影响
第三个例题 最长路径
类似于树的直径?
例题
综合运用
模板题
-
求以哪一个点为根时所有节点深度和最大 洛谷 P3478 [POI2008] STA-Station // Qiansui_code
本题做法与相关链接例题 距离和 一样 -
上题的小小强化版 洛谷 P2986 [USACO10MAR] Great Cow Gathering G // Qiansui_code
本题基本做法与上题一样,就是距离的定义发生了变化 -
简单换根DP cf 627 div.3 F. Maximum White Subtree // Qiansui_code
白色节点权值记为1,黑色节点权值记为-1,再跑标准的换根DP就行 -
稍微难一点的换根DP 洛谷 P3047 [USACO12FEB] Nearby Cows G // Qiansui_code
对每个节点都记录距离自己 0 ~ k 距离的节点权值和,先 dfs 一遍统计子树,再 dfs 一遍更新答案 -
再难一点的换根DP cf 899 div.2 D. Tree XOR // Qiansui_code
首先需要发现一点的是,对于一个有根树,无论你怎么执行操作,对于一组父子节点 uv,只要你不选择节点 v 进行操作,那么节点 u 和节点 v 的权值就永远不变。所以想要所有节点权值均相等,我们从根开始 dfs 遍历,遇到权值不相等的子节点则选择节点 v 异或
不可能对于每个节点都做一次dfs,那么考虑换根DP的做法。可以发现,当根节点从节点 u 传递给子节点 v 的时候,受到影响的答案只有节点 u 和节点 v 之间的关系。原本选择节点 v 进行修改操作,现在改为节点 u 进行修改操作即可,即
所以利用换根DP,可以
本文来自博客园,作者:Qiansui,转载请注明原文链接:https://www.cnblogs.com/Qiansui/p/17797839.html
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· 单线程的Redis速度为什么快?
· SQL Server 2025 AI相关能力初探
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
· 展开说说关于C#中ORM框架的用法!
2022-10-30 数论基础+裴蜀定理+线性同余方程+乘法逆元+中国剩余定理