题目背景

byx和手气君都非常都非常喜欢种树。有一天,他们得到了两颗奇怪的树种,于是各自取了一颗回家种树,并约定几年后比一比谁种出来的树更加牛x。

题目描述

很快,这棵树就开花结果了。byx和手气君惊讶的发现,这是一棵主席树,树上长满了主席和主席的朋友们。这棵树上一共有五种人,主席(J),记者(HK),高人(W),女王(E)和膜法师(YYY)。他们发现,他们的主席树上的人数相同,都为N。

研究发现,这五种人的输赢如上图所示(一样的人不能PK),箭头指向输的人。至于为什么,留给同学们自己思考。

比赛如期进行。

byx和手气君要进行M场比赛,每一场比赛他们会选出树上的两个人来比较看谁更牛x。

第i个人寿命为Lifei秒,每次比完赛他们就会-1s。当他们生命为0s时他们就不能再比赛了。

同时,当J的寿命为0时,同一棵树上的YYY可以为他+1s。每个YYY只能给.每个J续一次。

那么问题来了

现在给定N,M(1≤N≤100,1≤M≤1000),A和B每一个人所属种类(J,HK,W,YYY或E)以及每一个人的生命,生命不超过50.请你算算A最多能够赢得多少场比赛呢。

数据保证每一场一定都有人用。两个人之间只能比一场。

题目解析

其实没有那么难吧

最大流

S向byx的人连边,边权是寿命。手气君的人向T连边,边权是寿命。

如果byx的人向ta能战胜的手气君的人连边,边权是1。

然后DINIC

不过貌似什么地方写挂了,只有90。完了再填坑吧

Code

#include<iostream>
#include<cstdio>
#include<cstring>
#include<queue>
using namespace std; const int MAXN = + ;
const int MAXM = + ;
const int S = ;
const int T = ;
const int INF = 0x3f3f3f3f; struct Tree {
string name;
int life;
} a[MAXN],b[MAXN];
struct Edge {
int nxt;
int to,w;
} l[MAXN*MAXN*]; int n,m;
int maxflow;
int num[];
int head[MAXN*],cnt=;
int deep[MAXN*],cur[MAXN*]; inline void add(int x,int y,int z) {
cnt++;
l[cnt].nxt = head[x];
l[cnt].to = y;
l[cnt].w = z;
head[x] = cnt;
return;
} inline void build() {
for(int i = ;i <= n;i++) {
add(S,i,a[i].life);add(i,S,);
add(i+n,T,b[i].life);add(T,i+n,);
}
for(int i = ;i <= n;i++) {
for(int j = ;j <= n;j++) {
if(a[i].name == "W" && (b[j].name == "YYY" || b[j].name == "E")) add(i,j+n,),add(j+n,i,);
else if(a[i].name == "HK" && (b[j].name == "W" || b[j].name == "E")) add(i,j+n,),add(j+n,i,);
else if(a[i].name == "E" && (b[j].name == "J" || b[j].name == "YYY")) add(i,j+n,),add(j+n,i,);
else if(a[i].name == "YYY" && (b[j].name == "J" || b[j].name == "HK")) add(i,j+n,),add(j+n,i,);
else if(a[i].name == "J" && (b[j].name == "W" || b[j].name == "HK")) add(i,j+n,),add(j+n,i,);
}
}
return;
}
queue<int> Q;
inline bool bfs(){
memset(deep,,sizeof(deep));
while(Q.size()) Q.pop();
deep[S]=;Q.push(S);
while(Q.size()){
int x=Q.front();Q.pop();
for(register int i=head[x];i;i=l[i].nxt){
int u=l[i].to;
if(!deep[u] && l[i].w){
deep[u]=deep[x]+;
if(u==T) return true;
Q.push(u);
}
}
}
return false;
} int dfs(int x,int flow){
if(x==T) return flow;
int res=flow,k;
for(register int i=head[x];i && res;i=l[i].nxt){
int u=l[i].to;
if(l[i].w && deep[u]==deep[x]+){
k=dfs(u,min(l[i].w,res));
if(!k) deep[u]=;
l[i].w -= k;
res-=k;
}
}
return flow-res;
} inline void Dinic(int s,int t) {
while(bfs()) maxflow += dfs(s,INF);
return;
} int main() {
scanf("%d%d",&n,&m);
for(int i = ;i <= n;i++) {
cin>>a[i].name;
if(a[i].name == "YYY") num[]++;
}
for(int i = ;i <= n;i++) {
cin>>b[i].name;
if(b[i].name == "YYY") num[]++;
}
for(int i = ;i <= n;i++) {
scanf("%d",&a[i].life);
if(a[i].name == "J") a[i].life += num[];
}
for(int i = ;i <= n;i++) {
scanf("%d",&b[i].life);
if(b[i].name == "J") b[i].life += num[];
}
build();
Dinic(S,T);
int debug = min(m,maxflow);
if(debug == ) debug += ;//QAQ
printf("%d",debug);
return ;
}

[Luogu] P3701 「伪模板」主席树的更多相关文章

  1. [Luogu 3701] 「伪模板」主席树

    [Luogu 3701] 「伪模板」主席树 这是一道网络流,不是主席树,不是什么数据结构,而是网络流. 题目背景及描述都非常的暴力,以至于 Capella 在做此题的过程中不禁感到生命流逝. S 向 ...

  2. P3701 「伪模板」主席树

    题目背景 byx和手气君都非常都非常喜欢种树.有一天,他们得到了两颗奇怪的树种,于是各自取了一颗回家种树,并约定几年后比一比谁种出来的树更加牛x. 题目描述 很快,这棵树就开花结果了.byx和手气君惊 ...

  3. [洛谷P3701]「伪模板」主席树

    题目大意:太暴力了,就不写了,看这儿 题解:对于每个$byx$的人,从源点向人连边,容量为此人的寿命. 对于每个手气君的人,从人向汇点连边,容量为此人的寿命. 对于每个$byx$的人与手气君的人,如果 ...

  4. 【luoguP3701】「伪模板」主席树

    description byx和诗乃酱都非常都非常喜欢种树.有一天,他们得到了两颗奇怪的树种,于是各自取了一颗回家种树,并约定几年后比一比谁种出来的树更加牛x. 很快,这棵树就开花结果了.byx和诗乃 ...

  5. LuoguP3701 「伪模板」主席树

    题面 这个题很有意思啊... 其实是道最大流板子题,只连byx会赢的边,S向byx连,另一个连T... 注意有长者时连的边加上同方mogician的个数... 还要注意mogician可以无限续命,也 ...

  6. 「模板」 线段树——区间乘 && 区间加 && 区间求和

    「模板」 线段树--区间乘 && 区间加 && 区间求和 原来的代码太恶心了,重贴一遍. #include <cstdio> int n,m; long l ...

  7. 「WC 2019」数树

    「WC 2019」数树 一道涨姿势的EGF好题,官方题解我并没有完全看懂,尝试用指数型生成函数和组合意义的角度推了一波.考场上只得了 44 分也暴露了我在数数的一些基本套路上的不足,后面的 \(\ex ...

  8. 【题解】#6622. 「THUPC 2019」找树 / findtree(Matrix Tree+FWT)

    [题解]#6622. 「THUPC 2019」找树 / findtree(Matrix Tree+FWT) 之前做这道题不理解,有一点走火入魔了,甚至想要一本近世代数来看,然后通过人类智慧思考后发现, ...

  9. 【Luogu】P3384主席树模板(主席树查询K小数)

    YEAH!我也是一个AC主席树模板的人了! 其实是个半吊子 我将尽量详细的讲出我的想法. 主席树太难,我们先搞普通线段树好了 普通线段树怎么做?我的想法是查询K次最小值,每次查完把查的数改成INF,查 ...

随机推荐

  1. Error:(2, 0) No service of type Factory<LoggingManagerInternal> available in ProjectScopeServices. <

    compile报下面的错误Error:(2, 0) No service of type Factory available in ProjectScopeServices. 点击open file ...

  2. [LeetCode] Construct Binary Tree from Inorder and Pretorder Traversal

    Given preorder and inorder traversal of a tree, construct the binary tree. Note:You may assume that ...

  3. Linux 常用命令大全2

    Linux 常用命令大全 [帮助命令] command —help man command man 2 command 查看第2个帮助文件 man -k keyword 查找含有关键字的帮助 info ...

  4. 使用vue-cli启动项目出错

    Vue.js(读音 /vjuː/, 类似于 view) 是一套构建用户界面的渐进式框架. Vue 只关注视图层, 采用自底向上增量开发的设计. Vue 的目标是通过尽可能简单的 API 实现响应的数据 ...

  5. Spark 2.2.0 分布式集群环境搭建

    集群机器: 1台 装了 ubuntu 14.04的 台式机 1台 装了ubuntu 16.04 的 笔记本     (机器更多时同样适用) 1.需要安装好Hadoop分布式环境 参照:Hadoop分类 ...

  6. 在Android.mk文件中输出打印消息 (转载)

    转自:http://blog.csdn.net/xiaibiancheng/article/details/8479694 在进行Android NDK的开发当中有时想看看Android.mk文件当中 ...

  7. 符号修饰与函数签名、extern “C”(转载)

    转自:http://www.cnblogs.com/monotone/archive/2012/11/16/2773772.html 参考资料: <程序员的自我修养>3.5.3以及3.5. ...

  8. bzoj 1770: [Usaco2009 Nov]lights 燈【高斯消元+dfs】

    参考:https://blog.csdn.net/qq_34564984/article/details/53843777 可能背了假的板子-- 对于每个灯建立方程:与它相邻的灯的开关次数的异或和为1 ...

  9. P4161 [SCOI2009]游戏

    传送门 首先这题的本质就是把\(n\)分成若干个数的和,求他们的\(lcm\)有多少种情况 然后据说有这么个结论:若\(p_1^{c_1}+p_2^{c_2}+...+p_m^{c_m}\leq n\ ...

  10. Django day 36 支付宝支付,微信推送

    一:支付宝支付, 二:微信推送