1040: [ZJOI2008]骑士

Time Limit: 10 Sec  Memory Limit: 162 MB
Submit: 5368  Solved: 2044
[Submit][Status][Discuss]

Description

  Z国的骑士团是一个很有势力的组织,帮会中汇聚了来自各地的精英。他们劫富济贫,惩恶扬善,受到社会各
界的赞扬。最近发生了一件可怕的事情,邪恶的Y国发动了一场针对Z国的侵略战争。战火绵延五百里,在和平环境
中安逸了数百年的Z国又怎能抵挡的住Y国的军队。于是人们把所有的希望都寄托在了骑士团的身上,就像期待有一
个真龙天子的降生,带领正义打败邪恶。骑士团是肯定具有打败邪恶势力的能力的,但是骑士们互相之间往往有一
些矛盾。每个骑士都有且仅有一个自己最厌恶的骑士(当然不是他自己),他是绝对不会与自己最厌恶的人一同出
征的。战火绵延,人民生灵涂炭,组织起一个骑士军团加入战斗刻不容缓!国王交给了你一个艰巨的任务,从所有
的骑士中选出一个骑士军团,使得军团内没有矛盾的两人(不存在一个骑士与他最痛恨的人一同被选入骑士军团的
情况),并且,使得这支骑士军团最具有战斗力。为了描述战斗力,我们将骑士按照1至N编号,给每名骑士一个战
斗力的估计,一个军团的战斗力为所有骑士的战斗力总和。

Input

  第一行包含一个正整数N,描述骑士团的人数。接下来N行,每行两个正整数,按顺序描述每一名骑士的战斗力
和他最痛恨的骑士。

Output

  应包含一行,包含一个整数,表示你所选出的骑士军团的战斗力。

Sample Input

3
10 2
20 3
30 1

Sample Output

30

HINT

N ≤ 1 000 000,每名骑士的战斗力都是不大于 1 000 000的正整数。

  在开头先吐槽一下题面,”劫富济贫“是怎么得到社会"各界"的好评的?!  开个玩笑,这道题可以说是Bzoj1214枪战Maf的加强版没做过的可以先去做一下(附题解:[POI2008]枪战Maf题解)。
  对于这道题的种种性质我就不多说了,在那篇题解里基本都分析了。
  这两道题最大的不同就是这道题并不能用贪心做,也就是我们并不能再通过拓扑去得到答案。而是利用他的另一个性质:树。
  我们可以注意到,只要我们缩一下边,那么留给我们的就是一个树,或者树林,那么对于树的叶子节点,他们一定只是由一个骑士组成,所以我们只要简单的用两种状态记录一下选他和不选他的答案就好了。当我们爬到树根时,我们不必急着直接转移给他,而是转移给实际向该叶节点伸边的那个骑士,然后再环中随便找一个点开始一个dfs,反正只是简单环,出不了什么问题。再记录一下结算到但钱违者当前这个环你的切入点是否被选上然后在绕回来时转移给大点就好了。
  

 #include <cstdlib>
#include <cstdio>
#include <cstring>
#include <string>
#include <queue>
#include <algorithm>
#include <cmath>
#include <map>
#define N 1000005
using namespace std;
int n,to[N],zz1,zz,a[N],b[N];
long long va[N],vva[N];
struct ro
{
int to,next,fr;
}road2[N],road[N];
void build2(int x,int y)
{
zz1++;
road2[zz1].to=y;
road2[zz1].next=b[x];
b[x]=zz1;
}
void build(int x,int y,int z)
{
zz++;
road[zz].fr=z;
road[zz].to=y;
road[zz].next=a[x];
a[x]=zz;
}
int dfn[N],low[N],zz2,zz3,top,st[N],bel[N],sta[N],fa[N],size[N];
bool rd[N],rd2[N];
void tar(int x)
{
zz2++;top++;
st[top]=x;
dfn[x]=low[x]=zz2;
rd[x]=rd2[x]=;
for(int i=b[x];i>;i=road2[i].next)
{
int y=road2[i].to;
if(!rd2[y])
{
tar(y);
low[x]=min(low[x],low[y]);
}
else if(rd[y])
{
low[x]=min(dfn[y],low[x]);
}
}
if(dfn[x]==low[x])
{
zz3++;
int v;
do{
v=st[top];
rd[v]=;
top--;
bel[v]=zz3;
sta[zz3]=v;
size[zz3]++;
vva[zz3]+=va[v];
}while(dfn[v]!=low[v]);
}
}
long long f[N][],f2[N][][],f3[N][];
void dfs2(int x,int fr,int tp)
{
if(x==tp&&fr)
{
f2[x][][]=max(f2[fr][][],f2[fr][][]);
f2[x][][]=f2[fr][][];
f[bel[x]][]=max(f2[x][][],f2[x][][]);
return;
}
if(x==tp)
{
f2[x][][]+=f3[x][];
f2[x][][]+=f3[x][];
f2[x][][]+=va[x];
}
else
{
if(fr==tp)
{
f2[x][][]=f2[x][][]=f2[fr][][],f2[x][][]=f2[fr][][];
f2[x][][]+=f3[x][];f2[x][][]+=va[x];
f2[x][][]+=f3[x][];f2[x][][]+=f3[x][];
}
else
{
f2[x][][]=max(f2[fr][][],f2[fr][][]);
f2[x][][]=max(f2[fr][][],f2[fr][][]);
f2[x][][]=f2[fr][][];
f2[x][][]=f2[fr][][];
f2[x][][]+=va[x]+f3[x][];
f2[x][][]+=va[x]+f3[x][];
f2[x][][]+=f3[x][];
f2[x][][]+=f3[x][];
}
}
dfs2(to[x],x,tp);
}
void dfs1(int x)
{
for(int i=a[x];i>;i=road[i].next)
{
int y=road[i].to;
dfs1(y);
if(size[x]==)
{
f[x][]+=max(f[y][],f[y][]);
f[x][]+=f[y][];
}
else
{
f3[road[i].fr][]+=max(f[y][],f[y][]);
f3[road[i].fr][]+=f[y][];
}
}
if(size[x]==)f[x][]+=vva[x];
else
{
dfs2(sta[x],,sta[x]);
}
}
int main()
{
scanf("%d",&n);
for(int i=;i<=n;i++)
{
scanf("%lld%d",&va[i],&to[i]);
build2(to[i],i);
}
for(int i=;i<=n;i++)
{
if(!rd2[i])tar(i);
}
for(int i=;i<=n;i++)
{
for(int j=b[i];j>;j=road2[j].next)
{
int y=road2[j].to;
if(bel[i]!=bel[y])
{
build(bel[i],bel[y],i);
}
}
}
for(int i=;i<=zz3;i++)
{
if(size[i]!=)
{
dfs1(i);
}
}
long long ans=;
for(int i=;i<=zz3;i++)
{
if(size[i]!=)
{
ans+=f[i][];
}
}
printf("%lld\n",ans);
return ;
}

Bzoj 1040 [ZJOI2008]骑士 题解的更多相关文章

  1. [BZOJ 1040][ZJOI2008]骑士

    1040: [ZJOI2008]骑士 Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 5403  Solved: 2060[Submit][Status ...

  2. BZOJ 1040: [ZJOI2008]骑士 基环加外向树

    1040: [ZJOI2008]骑士 Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 1190  Solved: 465[Submit][Status] ...

  3. bzoj 1040: [ZJOI2008]骑士 環套樹DP

    1040: [ZJOI2008]骑士 Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 1755  Solved: 690[Submit][Status] ...

  4. bzoj 1040: [ZJOI2008]骑士 树形dp

    题目链接 1040: [ZJOI2008]骑士 Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 3054  Solved: 1162[Submit][S ...

  5. [BZOJ 1040] [ZJOI2008] 骑士 【基环+外向树DP】

    题目链接:BZOJ - 1040 题目分析 这道题目的模型就是一个图,不一定联通,每个连通块的点数等于边数. 每个连通块都是一个基环+外向树.即树上增加了一条边. 如果是树,就可以直接树形DP了.然而 ...

  6. BZOJ 1040: [ZJOI2008]骑士 | 在基环外向树上DP

    题目: http://www.lydsy.com/JudgeOnline/problem.php?id=1040 题解: 我AC了 是自己写的 超开心 的 考虑断一条边 这样如果根节点不选答案一定正确 ...

  7. bzoj 1040 [ZJOI2008]骑士(基环外向树,树形DP)

    [题目链接] http://www.lydsy.com/JudgeOnline/problem.php?id=1040 [题意] 给一个基环森林,每个点有一个权值,求一个点集使得点集中的点无边相连且权 ...

  8. BZOJ 1040: [ZJOI2008]骑士 [DP 环套树]

    传送门 题意:环套树的最大权独立集 一开始想处理出外向树树形$DP$然后找到环再做个环形$DP$ 然后看了看别人的题解其实只要断开环做两遍树形$DP$就行了...有道理! 注意不连通 然后洛谷时限再次 ...

  9. BZOJ 1040: [ZJOI2008]骑士(基环树dp)

    http://www.lydsy.com/JudgeOnline/problem.php?id=1040 题意: 思路: 这是基环树,因为每个人只会有一个厌恶的人,所以每个节点只会有一个父亲节点,但是 ...

随机推荐

  1. Win10《芒果TV》商店版更新v3.1.4.0:适配Xbox手柄B键后退、手机支持暗色主题不伤眼

    在双十一全球剁手节.光棍节欢庆之际,<芒果TV>UWP版迅速更新v3.1.4版,适配Xbox手柄B键全局后退,支持手机切换暗色主题,优化并解决启动卡顿等问题. 芒果TV UWP V3.1. ...

  2. Win10商店芒果TV UWP版更新,新增后台视频下载

    湖南卫视旗下唯一官方视频平台<芒果TV>近日向Win10商店提交了芒果TV UWP V3.0.0版,这次为广大Win10平台用户带来了期待已久的重大功能和更新,可谓是良心厂商,值得鼓励和支 ...

  3. Oracle配置OneMap中的sql数据库问题及解决方案

    报错ORA-00900:无效SQL语句,点确定后报错:ORA--00942:表或视图不存在 分析:prompt在Oracle中是打印功能,如果要在PLsql中执行带有prompt的sql文件就会报上面 ...

  4. CSS技巧分享:如何用css制作横排二级下拉菜单

    原文:CSS技巧分享:如何用css制作横排二级下拉菜单 导航菜单是每个网站所必备的功能,也是每个学习制作网站的朋友所必须接触的,如何用css样式制作一个简单漂亮的二级下拉菜单呢,下来小编就一步一步教大 ...

  5. js基础知识总结:函数

    函数内部的属性: arguments 和this是函数内部的两个特殊对象 arguments: function recursion(num){ if(num<=1){ return 1; }e ...

  6. Qt5.4.2Mingw编译配置opencv2.4.9

    1 下载所需工具 (1)qt-opensource-windows-x86-mingw491_opengl-5.4.2.exe  842M 下载地址https://download.qt.io/arc ...

  7. Google C++测试框架系列高级篇:第二章 让GTest学习打印自定义对象

    上一篇:更多关于断言的知识 原始链接:Teaching Google Test How to Print Your Values 词汇表 版本号:v_0.1 让GTest学习打印自定义对象 当一个断言 ...

  8. BITED数学建模七日谈之一:参加全国大学生数学建模比赛前你需要积累哪些

    大家好,我是数学中国的版主magic2728,非常高兴能够借助数学中国这个平台分享一些自己的经验,帮助大家在国赛的最后备战中能够最后冲刺提高.分享一共分为七个部分,分七天写给大家,下面是第一个部分:参 ...

  9. 前端视频转码flv->swf

    在项目中本来是要用<video>标签插入视频,但此标签不支持flv格式,上网也是搜了很多,试了很久才成功(其他格式不是很清楚你们可以尝试看看) 所用技术 flach (Flvplayer. ...

  10. javascript匿名函数自调用

    // 匿名函数的自调用 /*var f1 = function() { console.log('我是一个匿名函数!'); }*/ // f1(); // 上面是定义一个匿名函数,然后调用,其实上面就 ...