Codeforces Round #322 (Div. 2) F. Zublicanes and Mumocrates(树形dp)
来源:互联网 发布:vr视频软件 编辑:程序博客网 时间:2024/04/30 15:32
题意:
给定2≤N≤5000的一棵树,现在要将这棵树黑白染色
染色的要求是:叶子节点必须黑白对半(保证有偶数个叶子)
在满足染色要求的情况下,使得不同色节点连接的边数最少
求这个边数
分析:
树形dp
一开始定义状态dp[u][cnt][2]:=u这个节点染成0/1,整棵树有cnt个染成1的点,的最少不同色节点连接的边
发现根本没法转移,太年轻,树形dp的状态怎么能跟子树没关系呢。。
f[u][cnt][2]:=以u为根的这颗子树有cnt染成1的叶子,且u被染成0/1,的最少不同色节点连接的边
leaves[u]:=以u为根的这颗子树有多少个叶子
转移的时候,叶子节点显然f[u][1][1]=f[u][0][0]=0,leaves[u]=1
对于其他情况,只能暴力枚举染1色的叶子数,但要注意枚举u的染1色叶子数的时候,不能计算当前v这颗子树的叶子
由于需要枚举所有u的儿子,我们需要一个新的状态来帮助转移
g[0][cnt][2]:=只有u本身的情况,染成0/1,显然g[0][0][0]=g[0][0][1]=0
g[1][cnt][2]:=当前u的状态下,u的第1个儿子对u的转移
显然g我们可以滚动数组来对接受所有儿子的转移,最终得到整个u为根的子树的结果
将结果复制过去,f[u]=g[cur]
halfLeaves=leaves[root]/2, 显然ans=min(f[root][halfLeaves][0],f[root][halfLeaves][1])
所谓的根只要找到随便一个不是叶子的即可
显然我们需要特判n=2时,找不到根,ans=1
对于时间复杂度为啥是O(n2),题解说的是每对(x,y)对其总更新次数只在lca出贡献一次
表示不懂,不过看起来确实复杂度比O(n3)小
代码:
//// Created by TaoSama on 2016-02-02// Copyright (c) 2015 TaoSama. All rights reserved.//#pragma comment(linker, "/STACK:1024000000,1024000000")#include <algorithm>#include <cctype>#include <cmath>#include <cstdio>#include <cstdlib>#include <cstring>#include <iomanip>#include <iostream>#include <map>#include <queue>#include <string>#include <set>#include <vector>using namespace std;#define pr(x) cout << #x << " = " << x << " "#define prln(x) cout << #x << " = " << x << endlconst int N = 5e3 + 10, INF = 0x3f3f3f3f, MOD = 1e9 + 7;int n;int f[N][N][2], g[2][N][2], leaves[N]; //leaf to 1vector<int> G[N];void getMin(int &x, int y) { if(x > y) x = y;}void see(int u) { printf("%d:\n", u); for(int i = 0; i <= leaves[u]; ++i) for(int j = 0; j < 2; ++j) printf("f[%d][%d]=%d\n", i, j, f[u][i][j]); puts("");}void dfs(int u, int fa) { leaves[u] = 0; if(G[u].size() == 1) { leaves[u] = 1; f[u][0][0] = f[u][1][1] = 0; f[u][0][1] = f[u][1][0] = INF;// see(u); return; } for(int v : G[u]) { if(v == fa) continue; dfs(v, u); } int p = 0; g[p][0][0] = g[p][0][1] = 0; for(int v : G[u]) { if(v == fa) continue; memset(g[!p], 0x3f, sizeof g[!p]); for(int i = 0; i <= leaves[u]; ++i) for(int j = 0; j <= leaves[v]; ++j) for(int a = 0; a < 2; ++a) for(int b = 0; b < 2; ++b) getMin(g[!p][i + j][a], g[p][i][a] + f[v][j][b] + (a != b)); p = !p; leaves[u] += leaves[v]; } memcpy(f[u], g[p], sizeof g[p]);// see(u);}int main() {#ifdef LOCAL freopen("C:\\Users\\TaoSama\\Desktop\\in.txt", "r", stdin);// freopen("C:\\Users\\TaoSama\\Desktop\\out.txt","w",stdout);#endif ios_base::sync_with_stdio(0); while(scanf("%d", &n) == 1) { for(int i = 1; i <= n; ++i) G[i].clear(); for(int i = 1; i < n; ++i) { int u, v; scanf("%d%d", &u, &v); G[u].push_back(v); G[v].push_back(u); } if(n == 2) {puts("1"); continue;} for(int i = 1; i <= n; ++i) { if(G[i].size() > 1) {// printf("root:%d\n", i); dfs(i, -1); int cnt = leaves[i] >> 1; int ans = min(f[i][cnt][0], f[i][cnt][1]); printf("%d\n", ans); break; } } } return 0;}
- Codeforces Round #322 (Div. 2) F. Zublicanes and Mumocrates(树形dp)
- DP Codeforces Round #322 (Div. 2) F. Zublicanes and Mumocrates
- Codeforces Round #322 (Div. 2) F. Zublicanes and Mumocrates(树形dp,好题)
- Codeforces #322 div2. F Zublicanes and Mumocrates 树形dp
- CodeForces 581F Zublicanes and Mumocrates 树形DP
- 【树DP】[CodeForces - 581F]Zublicanes and Mumocrates
- codeforces Zublicanes and Mumocrates
- codeforces581F. Zublicanes and Mumocrates
- Codeforces Round #322 (Div. 2)F 树形背包
- Codeforces Round #358 (Div. 2) C Alyona and the Tree(树形DP)
- Codeforces Round #263 (Div. 2)D(树形DP)
- Codeforces Round #294 (Div. 2) E. A and B and Lecture Rooms(倍增LCA+树形DP)
- Codeforces Round #396 (Div. 2) E. Mahmoud and a xor trip(树形dp+二进制按位拆分)
- Codeforces Round #216 (Div. 2) C. Valera and Elections (树形dp)
- Codeforces Round #343 (Div. 2) E. Famil Door and Roads (树形dp,lca)
- Codeforces Round #358 (Div. 2)-C. Alyona and the Tree(树形dp)
- Codeforces Round #343 (Div. 2) E. Famil Door and Roads (树形dp,lca)★ ★ ★
- Codeforces Round #384(Div. 2)D. Chloe and pleasant prizes【树形dp】
- ubuntu14.04安装caffe+digits
- 【Android开发小记--8】传感器 以及 指南针的实现
- 计算机网络6--多路复用技术
- BO SDK - 列出所有 web intelligence 报表用到的 universe object
- Android基础之Fragment
- Codeforces Round #322 (Div. 2) F. Zublicanes and Mumocrates(树形dp)
- JavaScript
- hdu1512 Monkey King【左偏堆、并查集】
- MFC CListView 设置和获取item图片
- luajit ffi 小结
- HDU 2612 Find a way【双重BFS】
- Encoding
- vmware配置centos7网络
- open Linux