首页 > 其他分享 >CF375E Red and Black Tree

CF375E Red and Black Tree

时间:2022-08-31 20:22:39浏览次数:86  
标签:int void Tree dfn Black CF375E inline MAXN define

题目传送门

Solution

非常神奇的一道题。

我们不考虑交换操作,相反,我们去考虑把多少个 \(0\) 的位置变为 \(1\),同时我们记录选了多少个黑点,如果跟原来黑点数量相同即是合法。

此时我们可以发现一个神奇的性质对于 \(u\) 的儿子 \(v\),如果覆盖 \(u\) 的节点不覆盖 \(v\),那么覆盖 \(v\) 的节点在 \(v\) 的子树内的时候最优,因为不在的话会让覆盖 \(u\) 的节点变成覆盖 \(v\) 的节点。

所以我们可以考虑设 \(f_{u,i,k}\) 表示以 \(u\) 为根的子树,选了 \(i\) 个黑点,覆盖 \(u\) 的节点是 \(k\) 的最小需要把多少个白点变为黑点,然后我们可以树上背包。复杂度显然 \(\Theta(n^3)\)。

Code

#include <bits/stdc++.h>
using namespace std;

#define Int register int
#define MAXN 505
#define sh short

template <typename T> inline void read (T &t){t = 0;char c = getchar();int f = 1;while (c < '0' || c > '9'){if (c == '-') f = -f;c = getchar();}while (c >= '0' && c <= '9'){t = (t << 3) + (t << 1) + c - '0';c = getchar();} t *= f;}
template <typename T,typename ... Args> inline void read (T &t,Args&... args){read (t);read (args...);}
template <typename T> inline void write (T x){if (x < 0){x = -x;putchar ('-');}if (x > 9) write (x / 10);putchar (x % 10 + '0');}
template <typename T> inline void chkmax (T &a,T b){a = max (a,b);}
template <typename T> inline void chkmin (T &a,T b){a = min (a,b);}

#define pii pair<int,int>
#define se second
#define fi first
vector <pii> g[MAXN];

int n,X,tot,col[MAXN];
sh f[MAXN][MAXN][MAXN],h[MAXN][MAXN],miv[MAXN][MAXN];

int ind,tur[MAXN],dfn[MAXN],siz[MAXN];
void dfs (int u,int fa){
	dfn[u] = ++ ind,tur[ind] = u;
	for (pii it : g[u]){
		int v = it.fi;
		if (v ^ fa) dfs (v,u);
	}
}

void getdis (int u,int rt,int fa,int dis){
	if (u == rt) f[u][1][dfn[u]] = 1 ^ col[u];
	else f[rt][0][dfn[u]] = 0;
	for (pii it : g[u]){
		int v = it.fi,w = it.se;
		if (v != fa && dis + w <= X) getdis (v,rt,u,dis + w);
	}
}

void dfs1 (int u,int fa){
	siz[u] = 1;
	for (pii it : g[u]){
		int v = it.fi;
		if (v == fa) continue;
		dfs1 (v,u);
		for (Int i = 0;i <= siz[u];++ i) for (Int t = 1;t <= n;++ t) h[i][t] = f[u][i][t],f[u][i][t] = 0x3f3f;
		for (Int i = 0;i <= siz[u];++ i) for (Int t = 1;t <= n;++ t){
			for (Int j = 0;j <= siz[v] && i + j <= tot;++ j){
				chkmin (f[u][i + j][t],(sh)(h[i][t] + f[v][j][t]));
				if (t < dfn[v] || t >= dfn[v] + siz[v])
					chkmin (f[u][i + j][t],(sh)(h[i][t] + miv[v][j]));
			}
		}
		siz[u] += siz[v];
	}
	for (Int i = 0;i <= siz[u];++ i){
		miv[u][i] = 0x3f3f;
		for (Int k = dfn[u];k <= dfn[u] + siz[u] - 1;++ k) chkmin (miv[u][i],f[u][i][k]);
	}
}

signed main(){
	read (n,X);
	for (Int x = 1;x <= n;++ x) read (col[x]),tot += col[x];
	for (Int i = 2,u,v,w;i <= n;++ i) read (u,v,w),g[u].push_back ({v,w}),g[v].push_back ({u,w});
	dfs (1,0),memset (f,0x3f,sizeof (f));
	for (Int u = 1;u <= n;++ u) getdis (u,u,u,0);
	dfs1 (1,0);sh ans = n + 1;
	for (Int i = 0;i <= tot;++ i)
		for (Int j = 1;j <= n;++ j) 
			chkmin (ans,f[1][i][j]);
	write (ans == n + 1 ? -1 : ans),putchar ('\n');
	return 0;
}

标签:int,void,Tree,dfn,Black,CF375E,inline,MAXN,define
From: https://www.cnblogs.com/Dark-Romance/p/16644419.html

相关文章

  • element-ui tree权限树
    在权限中父子集不关联,一开始,我以为default-checked-keys值不对,最后看了文档,原来是check-strictly被开启了 <el-treeref="menu":......
  • CF620E NewYearTree
    题目链接  主要要实现区间覆盖和区间查询不同数,看见区间赋值操作可能会想到\(ODT\)来实现,区间查询不同数直接另外开一个数组记录一下就好了,但很可惜\(TLE\)了,代码如下:......
  • Vue中报npm WARN idealTree Removing dependencies.element-ui in favor of devDepend
    在添加element-ui的时候我是用的是:npmielement-ui--save-dev或npmielement-ui-S都会报错npmWARNidealTreeRemovingdependencies.element-uiinfavorofdevD......
  • C20220712T3 牛半仙的妹子Tree
    给定一棵树,要求执行3种操作:给树上某一结点涂色,从下一次操作起每一次向周围传染一个单位。树上所有点变为正常询问某个点是否被感染。\(n,m\leq10^5\)。首先想到暴......
  • LeetCode04. Maximum Depth of Binary Tree
    题意求一棵二叉树的深度方法DFS,更新当前最大深度代码voiddfs(TreeNode*root,int&height,int&ans){if(root==nullptr)return;height++;......
  • el-select和el-tree一起用
    html代码<el-form-itemlabel="树型结构"><el-selectv-model="treeData"placeholder="请选择..."style="width:16rem"><el-option:v......
  • VScode-TodoTree 待办事项插件的定制和使用
    VScode-TodoTree待办事项插件的定制和使用背景写代码过程中,突然发现一个Bug,但是又不想停下来手中的活,以免打断思路,怎么办?按代码编写会规范,都是建议在代码中加个TODO......
  • 动态获取部门(el-tree-select)自定义键名
    <el-tree-selectcheck-strictlysize="large":props="treeProps":data="datas.dataTree"v-model="d......
  • 110.balanced-binary-tree 平衡二叉树
    获取左右子树的高度,如果左右子树高度差小于等于1,则判断左右子树的左右子树,如此递归下去。classSolution{public:intgetDp(TreeNode*root){if(root......
  • 222.count-complete-tree-nodes 完全二叉树的节点个数
    遍历法遍历所有节点的方法,时间复杂度为\(O(n)\)classSolution{public:intcountNodes(TreeNode*root){if(root==nullptr)return0......