poj2054(贪心)
来源:互联网 发布:斗战神帐号淘宝 编辑:程序博客网 时间:2024/06/06 21:43
题意:有一棵树,每个节点都有一个代价基值Ci。现在要给每个点染色,第一个染根节点,其余的节点染色的时候其父节点必须已染色。每个节点染色会用掉一个时间单位,每个节点染色的代价是染完此节点时的总时间T*Ci。问染完全部节点所需要的最小代价。
解法:这道题真的略吊,不过最终我还是看了网上的题解才会做的。每次基值最大的节点一定会是在父节点染完色后马上进行染色的,然后可以假想此节点就可以和父节点合体为一个节点。这个时候基值就变成了合体中的平均值(证明略仔细想想可以想明白)。这个算法大概就是个贪心,有点像克鲁斯卡尔求最小生成树那样,一块一块解决,最后全部归一就解决了整个问题。由于自己写的有点麻烦,wa了几发,还是太弱了,继续学习。。。
发一个对这道题解释很好的一个博客:http://www.cnblogs.com/yu-chao/archive/2012/02/19/2358565.html
我的代码:
解法:这道题真的略吊,不过最终我还是看了网上的题解才会做的。每次基值最大的节点一定会是在父节点染完色后马上进行染色的,然后可以假想此节点就可以和父节点合体为一个节点。这个时候基值就变成了合体中的平均值(证明略仔细想想可以想明白)。这个算法大概就是个贪心,有点像克鲁斯卡尔求最小生成树那样,一块一块解决,最后全部归一就解决了整个问题。由于自己写的有点麻烦,wa了几发,还是太弱了,继续学习。。。
发一个对这道题解释很好的一个博客:http://www.cnblogs.com/yu-chao/archive/2012/02/19/2358565.html
我的代码:
#include <iostream>#include <stdio.h>#include <cstring>#include <vector>#include <queue>using namespace std;struct edge{ int v,next;} edges[100000];int head[1010];int count1=0;void addedge(int u,int v){ edges[count1].v=v; edges[count1].next=head[u]; head[u]=count1++;}double num[1010];int mount[1010];int parent[1010];bool rem[1010];struct point{ double stan; int order;};bool operator<(point a,point b){ return a.stan<b.stan;}priority_queue<point> que;int root;int n;int main(){ while(scanf("%d%d",&n,&root)==2) { while(!que.empty()) que.pop(); if(n==0&&root==0) break; double ans=0; count1=0; memset(head,-1,sizeof head); memset(rem,0,sizeof rem); for(int i=1;i<=n;i++) { mount[i]=1; scanf("%lf",num+i); point p;p.stan=num[i];p.order=i; que.push(p); } for(int i=0;i<n-1;i++) { int a,b; scanf("%d%d",&a,&b); parent[b]=a; addedge(a,b); } for(int i=0;i<n-1;i++) { while(rem[que.top().order]||que.top().order==root) que.pop(); point p=que.top(); que.pop(); int pre=parent[p.order]; ans+=p.stan*mount[p.order]*mount[pre]; for(int i=head[p.order];i!=-1;i=edges[i].next) { int a=edges[i].v; parent[a]=parent[p.order]; addedge(parent[p.order],a); } rem[p.order]=1; point tool;tool.order=parent[p.order]; tool.stan=double(p.stan*mount[p.order]+num[pre]*mount[pre])/double(mount[p.order] +mount[pre]); num[pre]=tool.stan;mount[pre]+=mount[p.order]; que.push(tool); } printf("%.0f\n",ans+mount[root]*num[root]); } return 0;}/*5 11 2 1 2 41 21 32 43 53 11 1 31 21 34 11 1 1 11 22 33 4*/
0 0
- poj2054(贪心)
- Poj2054 贪心
- poj2054
- poj2054
- color a tree【hdu1055】【POJ2054】贪心
- 几道贪心题目 POJ1328 radar installation POJ2054 color a tree
- POJ2054--Triangle
- poj2054 精品好题
- poj2054 Color a Tree
- POJ2054.Color a Tree
- HDU1055 POJ2054 Color a Tree
- 贪心(bnuoj49103+二分+贪心)
- 【贪心算法(一)】贪心算法基础
- zoj1002_FireNet(贪心法)
- 贪心题目(SOJ)
- POJ2718(枚举 + 贪心)
- POJ 1328(贪心)
- POJ 1818(贪心)
- 阿牛的EOF牛肉串
- java 常见问题 之 异常处理不彻底
- 用移动硬盘安装CentOS 6.5
- java实现生产者消费者问题
- 直方图匹配方法
- poj2054(贪心)
- 使用法国SOLEN电容有感
- [Vim]UTF-8乱码问题
- [Leetcode] Same Tree (Java)
- Mini2440移植qt-extended4.4.3
- 交叉编译opencv2.31与移植至arm9
- 算法导论9-2-c-带权中位数
- QT Creator和MinGW中配置OpenCV2.3.1
- CCI: Sort a stack