【BZOJ1565】【NOI2009】植物大战僵尸 网络流 最大权闭合子图
题目大意
 给你一个\(n\times m\)的地图,每个格子上都有一颗植物,有的植物能保护其他植物。僵尸从右往左进攻,每吃掉一颗植物就可以得到\(a_{i,j}\)的收益(\(a_{i,j}\)可以是负数)。求僵尸的最大收益
 \(1\leq n\leq20,1\leq m\leq30\)
题解
 这种一个东西可以保护另一个东西而且数据范围那么小的题目显然是最大权闭合子图。
 僵尸从右往左进攻,所以一棵植物可以保护它左边的植物。
 如果保护关系形成一个环,就都不能选。
 直接套模板即可。
 可能需要一些优化
代码
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cstdlib>
#include<ctime>
#include<utility>
#include<queue>
using namespace std;
typedef long long ll;
typedef pair<int,int> pii;
struct list
{
	int v[1000010];
	int w[1000010];
	int t[1000010];
	int h[1010];
	int n;
	list()
	{
		memset(h,0,sizeof h);
		n=0;
	}
	void add(int x,int y,int z)
	{
		n++;
		v[n]=y;
		w[n]=z;
		t[n]=h[x];
		h[x]=n;
	}
};
list l,l2;
void add(int x,int y,int z)
{
	l.add(x,y,z);
	l.add(y,x,0);
}
int n,m;
int w[110][110];
int gx[1010];
int gy[1010];
int id(int x,int y)
{
	return (x-1)*m+y;
}
int vis[1010];
int b[1010];
void dfs(int x)
{
	vis[x]=1;
	int i;
	for(i=l2.h[x];i;i=l2.t[i])
	{
		if(!vis[l2.v[i]])
			dfs(l2.v[i]);
		if(b[l2.v[i]]||vis[l2.v[i]]==1)
		{
//			w[gx[x]][gy[x]]=-10000000;
			b[x]=1;
		}
	}
	vis[x]=2;
}
int d[1010];
int S,T;
int c[30][40][30][40];
int bfs()
{
	memset(d,-1,sizeof d);
	queue<int> q;
	q.push(S);
	d[S]=0;
	int x,i;
	while(!q.empty())
	{
		x=q.front();
		q.pop();
		for(i=l.h[x];i;i=l.t[i])
			if(l.w[i]&&d[l.v[i]]==-1)
			{
				d[l.v[i]]=d[x]+1;
				if(l.v[i]==T)
					return 1;
				q.push(l.v[i]);
			}
	}
	return 0;
}
int op(int x)
{
	return ((x-1)^1)+1;
}
int dfs(int x,int flow)
{
	if(x==T)
		return flow;
	int c,s=0,i;
	for(i=l.h[x];i;i=l.t[i])
		if(l.w[i]&&d[l.v[i]]==d[x]+1)
		{
			c=dfs(l.v[i],min(flow,l.w[i]));
			s+=c;
			flow-=c;
			l.w[i]-=c;
			l.w[op(i)]+=c;
			if(!flow)
				break;
		}
	if(flow)
		d[x]=-1;
	return s;
}
int main()
{
	memset(b,0,sizeof b);
	memset(c,0,sizeof c);
//	freopen("bzoj1565.in","r",stdin);
//	freopen("bzoj1565.out","w",stdout);
	scanf("%d%d",&n,&m);
	S=n*m+1;
	T=S+1;
	int sum=0;
	int i,j,k,o,x,y,u;
	for(i=1;i<=n;i++)
		for(j=1;j<=m;j++)
		{
			scanf("%d",&w[i][j]);
			gx[id(i,j)]=i;
			gy[id(i,j)]=j;
			scanf("%d",&u);
			for(k=1;k<=u;k++)
			{
				scanf("%d%d",&x,&y);
				x++;
				y++;
				c[i][j][x][y]=1;
			}
			if(j>1)
				c[i][j][i][j-1]=1;
			for(x=1;x<=n;x++)
				for(y=1;y<=m;y++)
					if(c[i][j][x][y])
						l2.add(id(x,y),id(i,j),0);
		}
	memset(vis,0,sizeof vis);
	for(i=1;i<=n;i++)
		for(j=1;j<=m;j++)
			if(!vis[id(i,j)])
				dfs(id(i,j));
	for(i=1;i<=n;i++)
		for(j=1;j<=m;j++)
			if(!b[id(i,j)])
			{
				if(w[i][j]>0)
				{
					sum+=w[i][j];
					add(S,id(i,j),w[i][j]);
				}
				else
					add(id(i,j),T,-w[i][j]);
				for(x=1;x<=n;x++)
					for(y=1;y<=m;y++)
						if(c[i][j][x][y])
							if(!b[id(x,y)])
								add(id(x,y),id(i,j),0x7fffffff);
			}
	int ans=0;
	while(bfs())
		ans+=dfs(S,0x7fffffff);
	printf("%d\n",sum-ans);
	return 0;
}
												
											【BZOJ1565】【NOI2009】植物大战僵尸 网络流 最大权闭合子图的更多相关文章
- BZOJ1565 [NOI2009]植物大战僵尸  【最大权闭合子图 + tarjan缩点(或拓扑)】
		
题目 输入格式 输出格式 仅包含一个整数,表示可以获得的最大能源收入.注意,你也可以选择不进行任何攻击,这样能源收入为0. 输入样例 3 2 10 0 20 0 -10 0 -5 1 0 0 100 ...
 - [BZOJ1565][NOI2009]植物大战僵尸-[网络流-最小割+最大点权闭合子图+拓扑排序]
		
Description 传送门 Solution em本题知识点是用网络流求最大点权闭合子图. 闭合图定义:图中任何一个点u,若有边u->v,则v必定也在图中. 建图:运用最小割思想,将S向点权 ...
 - bzoj1565: [NOI2009]植物大战僵尸 最大权闭合子图,tarjan
		
bzoj1565: [NOI2009]植物大战僵尸 链接 https://www.lydsy.com/JudgeOnline/problem.php?id=1565 思路 很容易的想到最大权闭合子图 ...
 - BZOJ1565 [NOI2009]植物大战僵尸(拓扑排序 + 最大权闭合子图)
		
题目 Source http://www.lydsy.com/JudgeOnline/problem.php?id=1565 Description Input Output 仅包含一个整数,表示可以 ...
 - BZOJ1565[NOI2009]植物大战僵尸——最大权闭合子图+拓扑排序
		
题目描述 Plants vs. Zombies(PVZ)是最近十分风靡的一款小游戏.Plants(植物)和Zombies(僵尸)是游戏的主角,其中Plants防守,而Zombies进攻.该款游戏包含多 ...
 - [bzoj1565][NOI2009]植物大战僵尸_网络流_拓扑排序
		
植物大战僵尸 bzoj1565 题目大意:给你一张网格图,上面种着一些植物.你从网格的最右侧开始进攻.每个植物可以对僵尸提供能量或者消耗僵尸的能量.每个植物可以保护一个特定网格内的植物,如果一个植物被 ...
 - BZOJ 1565 [NOI2009]植物大战僵尸 | 网络流
		
传送门 BZOJ 1565 题解 这道题也是个经典的最大权闭合子图-- 复习一下最大权闭合子图是什么? 就是一个DAG上,每个点有个或正或负的点权,有的点依赖于另外一些点(如果选这个点,则被依赖点必选 ...
 - 洛谷$P2805\ [NOI2009]$植物大战僵尸 网络流
		
正解:网络流 解题报告: 传送门$QwQ$ 题面好长昂,,,我大概概括下$QwQ$?有个$n\cdot m$的网格,每个格子有一株植物,击溃一株植物$(x,y)$需要付出$S_{(x,y)}$的代价( ...
 - BZOJ 1565 植物大战僵尸(最大权闭合图)
		
题目链接:http://61.187.179.132/JudgeOnline/problem.php?id=1565 题意:植物大战僵尸,一个n*m的格子,每 个格子里有一个植物,每个植物有两个属性: ...
 
随机推荐
- 配置linux-Fedora系统下iptables防火墙
			
参考地址:https://blog.csdn.net/zhangjingyi111/article/details/78902820 本篇文章为实验课过程记录,较为简略. 1.查看系统是否安装ipta ...
 - docker之导出、导入、数据搬迁
			
docker 导出 导入有二种,一种是备份镜像,一种备份容器.数据搬迁,最简单粗暴就是直接COPY,volume的路径就行了. 一.导出导入镜像 #导出为tar docker save #ID or ...
 - hadoop实例-网站用户行为分析
			
一.数据集 网站用户购物行为数据集2030万条,包括raw_user.csv(2000万条)和small_user.csv(30万条,适合新手) 字段说明: user_id 用户编号,item_id ...
 - 3proxy使用方法
			
转自:DRL@fireinice写的教程 ******************************************************************************* ...
 - # 【Python3练习题 007】 有一对兔子,从出生后第3个月起每个月都生一对兔子, # 小兔子长到第三个月后每个月又生一对兔子, # 假如兔子都不死,问每个月的兔子总数为多少?
			
# 有一对兔子,从出生后第3个月起每个月都生一对兔子,# 小兔子长到第三个月后每个月又生一对兔子, # 假如兔子都不死,问每个月的兔子总数为多少?这题反正我自己是算不出来.网上说是经典的“斐波纳契数列 ...
 - css 图片文字垂直居中
			
先来看张图片 相信很多css新手遇到过这种问题,就是当图片和文本显示在一行的时候,效果很奇葩,文字和图片没法对齐, 这时我们需要做的是: 1,先给块级元素设置 display: inline-bloc ...
 - 12 Connections
			
1 and 出现在两个及以上的词,词组,或者句子之间,将它们连接起来.在正式的书面英语中,and不能出现在句首.在非正式的英语中可以. We should expand our product lin ...
 - 2 Modals of necessity
			
1 情况动词must 和词组have to, need to ,have got to 都表示必须做某事或者要求做某事. need to have to must have got to When ...
 - API知识点总结
			
一.开发api接口开放给其他人调用的api接口(短信接口,支付宝api) 二.api安全弱点数据窃取(解决加密),数据篡改(解决MD5),数据泄露(爬虫技术)(解决令牌)1.加密(HTTPS传输-收费 ...
 - Maven 项目 无缘无故报错:版本冲突,其他机器上正常-提交的时候报冲突怎么也解决不掉
			
2018年: maven突然之间报错了,显示版本冲突,但是其他的机器是好的, 使用命令:mvn compile -P dev -e; 看看测试环境有没有问题,还是有问题.而且,刚开始只是报错:erro ...