Codeforces Round #646 (Div. 2)E. Tree Shuffling 题解(dfs)
题目链接
题目大意
给你一颗树,每一个节点有一个a[i],b[i],c[i]值,你要把b[i]变成c[i],b[i]和c[i]为[0,1],你操作的方法是,选择一个节点x,选择他的k个子树,然后进行交换他们的b[i]值,使满足要求,每次操作的cost为a[x]*k,求满足题目要求所需要的最小cost,如果不能满足要求,则输出-1.
题目思路
基本思路想到了,但是不会实现,码力太差,直接放标准解析。
Key Idea: Let the parent of node i be p. If a[i]≥a[p], we can do the shuffling which was done at i, at p instead. Thus, we can do the operation a[i]=min(a[i],a[p]).
Detailed Explanation: Let us denote nodes that have bi=1 and ci=0 as type 1, and those that have bi=0 and ci=1 as type 2. Firstly, the answer is −1 if and only if the number of nodes of type 1 and type 2 are unequal.
We also observe that only nodes of type 1 and 2 should be shuffled - it is unoptimal to shuffle those which already have b[i]=c[i]. Thus, we should try to exchange the values of type 1 and type 2 nodes.
We use the key idea by going down from the root, and at every node i, setting a[i]=min(a[i],a[p]) where p is the parent node of i in the tree. Thus, the a[i]'s now follow a special structure: they are non-increasing from the root to the leaves!
This paves the way for our greedy solution: we will go upwards from the leaves, and at each node i interchange type 1 and type 2 nodes until we have no nodes in one of these types. Then, we pass on the remaining nodes to the parent to be shuffled.
代码
#include<cstdio>
#include<algorithm>
using namespace std;
typedef long long ll;
const int maxn=2e5+5;
int n,a[maxn],b[maxn],c[maxn],head[maxn],cnt;
ll cost;
struct node{int to,next;
}e[maxn<<1];
void add(int u,int v){e[++cnt].to=v;e[cnt].next=head[u];head[u]=cnt;
}
pair<int,int> dfs(int son,int fa,int mi){pair<int,int> x;x.first=x.second=0;if(b[son]==1&&c[son]==0){x.first++;}else if(b[son]==0&&c[son]==1){x.second++;}for(int i=head[son];i;i=e[i].next){if(e[i].to!=fa){pair<int,int> y=dfs(e[i].to,son,min(mi,a[son]));x.first+=y.first;x.second+=y.second;}}if(a[son]<=mi){int take=min(x.first,x.second);cost+=1ll*2*take*a[son];x.first-=take;x.second-=take;}return x;
}
int main(){scanf("%d",&n);for(int i=1;i<=n;i++){scanf("%d %d %d",&a[i],&b[i],&c[i]);}for(int i=1,u,v;i<=n-1;i++){scanf("%d %d",&u,&v);add(u,v),add(v,u);}pair<int,int> ans=dfs(1,1,a[1]);if(ans.first==0&&ans.second==0){printf("%lld\n",cost);}else{printf("-1\n");}return 0;
}
Codeforces Round #646 (Div. 2)E. Tree Shuffling 题解(dfs)相关推荐
- Codeforces Round #646 (Div. 2) E(贪心,bfs)
Codeforces Round #646 (Div. 2) E 题目大意: 给一棵树,每个节点有三个权值 A,B,C, (B,C为0或1),每次你可以花费 A[u] *k的代价让A子树中的任意 k ...
- Codeforces Round #807 (Div. 2)A~E个人题解
Dashboard - Codeforces Round #807 (Div. 2) - Codeforces A. Mark the Photographer 题意: 有个人,每个人的身高设为,现在 ...
- Codeforces Round #731 (Div. 3) G. How Many Paths? dfs + 拓扑 + 思维
传送门 题意: 给你一张nnn个点mmm条边的图,让你对每个点确定一个编号,规则如下: (1)(1)(1) 对于不能到的点编号为000. (2)(2)(2) 对于只有一条路径能到这个点的点编号为111 ...
- Codeforces Round #706 (Div. 2)-A. Split it!-题解
目录 Codeforces Round #706 (Div. 2)-A. Split it! Problem Description Input Output Sample Input Sample ...
- Codeforces Round #742 (Div. 2) B、C 题解
Codeforces Round 742 B. MEXor Mixup 题意 有一个数组,输入两个数a,b,a代表这个数组之外的最小非负整数,b代表这个数组的异或值,问你该数组的最小长度. 思路 首先 ...
- Codeforces Round #308 (Div. 2) C. Vanya and Scales dfs
题目链接: http://codeforces.com/contest/552/problem/C 题意: 给你100个砝码,第i个砝码质量是w^i,然后问你能不能在有m的情况下,左边和右边都放砝码, ...
- Codeforces Round #316 (Div. 2) D. Tree Requests dfs序
题目链接: 题目 D. Tree Requests time limit per test:2 seconds memory limit per test:256 megabytes 问题描述 Rom ...
- Codeforces Round #506 (Div. 3) - E. Tree with Small Distances
题目链接 题意 给你一棵树,最多加几条边,使点1到所有的点的最大距离不超过2 AC 贪心 从距离最远的点开始,找到他的父节点,然后把父节点相连的点删去,这样最好的情况可以删除三层点 遍历树的时候有两种 ...
- Codeforces Round #321 (Div. 2) C. Kefa and Park dfs
C. Kefa and Park Time Limit: 1 Sec Memory Limit: 256 MB 题目连接 http://codeforces.com/contest/580/probl ...
最新文章
- 布尔类型和三目运算符
- BZOJ4589: Hard Nim(FWT 快速幂)
- c语言ffffff错误,C语言打印16进制出现0xffffff现象的问题剖析!
- 52个实用的数据可视化工具!
- [C#]打包项目[转]
- 通过java.net.URLConnection发送HTTP请求的方法
- 面对女人的喋喋不休时,男人内心的真实想法
- Python 绘制热力图参数详解
- hhkb mac设置_把 HHKB 放在 MacBook 上使用的解决方案
- python 行为驱动_什么是行为驱动的Python?
- centos mysql5.6.35_centos6.8 mysql 5.6.35 glibc安装
- 软件测试国际化测试指标,国际化软件测试内容解析(2)
- JZOJ7月18日提高组T3 Ocd
- ioncube linux,linux 下ionCube安装
- 100以内的质数(基础算法)
- 宾州州立计算机科学世界排名,美国宾州州立大学排名和各专业排名
- excel 中如何设置误差线以及其意义
- 中国最缺大学的重点城市
- C#制作一个简易抽奖或摇号器
- 哪里能找到搞笑自媒体素材?学会技巧才能提高创作效率