Luogu 2762 太空飞行计划 / Libre 6001 「网络流 24 题」太空飞行计划 (网络流,最大流)

Description

W 教授正在为国家航天中心计划一系列的太空飞行。每次太空飞行可进行一系列商业性实验而获取利润。现已确定了一个可供选择的实验集合E={E1,E2,…,Em},和进行这些实验需要使用的全部仪器的集合I={ I1, I2,…,In }。实验Ej 需要用到的仪器是I的子集Rj∈I。 配置仪器Ik 的费用为ck 美元。实验Ej 的赞助商已同意为该实验结果支付pj 美元。W教授的任务是找出一个有效算法,确定在一次太空飞行中要进行哪些实验并因此而配置哪些仪器才能使太空飞行的净收益最大。这里净收益是指进行实验所获得的全部收入与配置仪器的全部费用的差额。

对于给定的实验和仪器配置情况,编程找出净收益最大的试验计划。

Input

第1行有2个正整数m和n(m,n <= 100)。m是实验数,n是仪器数。

接下来的m行,每行是一个实验的有关数据。第一个数赞助商同意支付该实验的费用;接着是该实验需要用到的若干仪器的编号。最后一行的n个数是配置每个仪器的费用。

Output

第1行是实验编号;第2行是仪器编号;最后一行是净收益。

Sample Input

2 3

10 1 2

25 2 3

5 6 7

Sample Output

1 2

1 2 3

17

Http

Luogu:https://www.luogu.org/problem/show?pid=2762

Libre:https://loj.ac/problem/6001

Source

网络流,最大流

解决思路

这道题要把其转换到网络流模型上不是很好理解。

首先我们来看一看构图

对于每一个实验,从源点到实验连一条流量为赞助商支付的钱的边;对于每一个仪器,从仪器到汇点连一条流量为仪器花费的边。对于每一个实验所需要的仪器,在实验与仪器之间连一条流量无穷大的边。在这张图上跑一边最大流,就可以得到最小的花费,再用总赞助商的支付钱减去这个花费即可。

为什么这样是对的呢?

从源点到实验的边保证了赞助商资助该实验不会超过赞助商的钱,而从仪器到汇点的边则保证了仪器最多只会花费掉这么多的钱

那么最后如何统计答案呢?

由于我们使用的是Dinic求最大流,那么我们可以直接借助层次图的depth数组来求解。因为最后要选取的实验必须是盈利的,所以从源点到盈利的实验的边一定一不满流的,那么也就是说在最后一遍bfs中一定会分配深度,那么我们只要找出depth不为0的实验即可。

同时,由于如果选择做某个实验就要花费其所有需要的仪器,我们可以在求出选择的实验的同时标记出要选择的仪器,最后再输出即可。

另:关于Dinic算法,请移步我的这篇文章

注:Libre的字符串读入似乎有些问题,容易出现RE

代码

#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<algorithm>
using namespace std; const int maxN=1000;
const int maxM=maxN*maxN*4;
const int inf=147483647; class Edge
{
public:
int v,flow;
}; int n,m;
int cnt=-1;
int Head[maxN];
int Next[maxM];
Edge E[maxM];
int depth[maxN];
int cur[maxN];
int Q[maxM];
bool chose[maxN];//标记某个仪器是否被选择
char str[maxM];//读入时要用到的字符串 void Add_Edge(int u,int v,int flow);
bool bfs();
int dfs(int u,int flow); int main()
{
int sum=0;
memset(Head,-1,sizeof(Head));
scanf("%d%d",&m,&n);
char ch=getchar();
while (ch!='\n')
ch=getchar();
for(int i=1;i<=m;++i)
{
int v;
scanf("%d",&v);
Add_Edge(0,i,v);//连接源点与实验
sum+=v;
memset(str,0,sizeof(str));
cin.getline(str,maxM);
int j=0;
while(sscanf(str+j,"%d",&v)==1)//注意这里的读入
{
if(!v)
j++;
else
Add_Edge(i,v+m,inf);//连接实验与仪器
while(v)
v/=10,j++;
j++;
}
}
/*
for (int i=1;i<=m;i++)//这是原来的字符串读入,会RE,有时还WA
{
int v;
scanf("%d",&v);
sum+=v;
Add_Edge(0,i,v);
ch=getchar();
do
{
while (((ch>'9')||(ch<'0'))&&(ch!='\n'))
ch=getchar();
if (ch=='\n')
break;
v=0;
while ((ch>='0')&&(ch<='9'))
{
v=v*10+ch-48;
ch=getchar();
}
///mcnt++;
Add_Edge(i,v+m,inf);
}
while (1);
}*/
for (int i=1;i<=n;i++)
{
int v;
scanf("%d",&v);
Add_Edge(i+m,n+m+1,v);//连接仪器与汇点
}
int Flow=0;
while (bfs())//Dinic
{
for (int i=0;i<=n+m+1;i++)
cur[i]=Head[i];
while (int di=dfs(0,inf))
Flow+=di;
}
memset(chose,0,sizeof(chose));
for (int i=1;i<=m;i++)//找出选择的实验
if (depth[i]!=-1)
{
printf("%d ",i);
for (int j=Head[i];j!=-1;j=Next[j])//同时标记要选择的仪器
chose[E[j].v-m]=1;
}
cout<<endl;
for (int i=1;i<=n;i++)
if (chose[i]==1)
printf("%d ",i);
cout<<endl;
cout<<sum-Flow<<endl;
return 0;
} void Add_Edge(int u,int v,int flow)//添加边
{
cnt++;
Next[cnt]=Head[u];
Head[u]=cnt;
E[cnt].v=v;
E[cnt].flow=flow; cnt++;
Next[cnt]=Head[v];
Head[v]=cnt;
E[cnt].v=u;
E[cnt].flow=0;
return;
} bool bfs()//构建层次图
{
memset(depth,-1,sizeof(depth));
int h=1,t=0;
Q[1]=0;
depth[0]=1;
do
{
t++;
int u=Q[t];
for (int i=Head[u];i!=-1;i=Next[i])
{
int v=E[i].v;
if ((E[i].flow>0)&&(depth[v]==-1))
{
depth[v]=depth[u]+1;
h++;
Q[h]=v;
}
}
}
while (h!=t);
if (depth[n+m+1]==-1)
return 0;
return 1;
} int dfs(int u,int flow)//增广
{
if (u==n+m+1)
return flow;
for (int &i=cur[u];i!=-1;i=Next[i])
{
int v=E[i].v;
if ((E[i].flow>0)&&(depth[v]==depth[u]+1))
{
int di=dfs(v,min(flow,E[i].flow));
if (di>0)
{
E[i].flow-=di;
E[i^1].flow+=di;
return di;
}
}
}
return 0;
}

Luogu 2762 太空飞行计划 / Libre 6001 「网络流 24 题」太空飞行计划 (网络流,最大流)的更多相关文章

  1. LibreOJ #6001. 「网络流 24 题」太空飞行计划 最大权闭合图

    #6001. 「网络流 24 题」太空飞行计划 内存限制:256 MiB时间限制:1000 ms标准输入输出 题目类型:传统评测方式:Special Judge 上传者: 匿名 提交提交记录统计讨论测 ...

  2. LOJ6001 - 「网络流 24 题」太空飞行计划

    原题链接 Description 有个实验和个仪器,做实验有报酬买仪器有花费.每个实验都需要一些仪器,求最大净收益(实验报酬仪器花费),并输出一组方案. Solution 实验向所需仪器连边,实验的点 ...

  3. Libre 6013 「网络流 24 题」负载平衡 (网络流,最小费用最大流)

    Libre 6013 「网络流 24 题」负载平衡 (网络流,最小费用最大流) Description G 公司有n 个沿铁路运输线环形排列的仓库,每个仓库存储的货物数量不等.如何用最少搬运量可以使n ...

  4. Libre 6010「网络流 24 题」数字梯形 (网络流,最大费用最大流)

    Libre 6010「网络流 24 题」数字梯形 (网络流,最大费用最大流) Description 给定一个由n 行数字组成的数字梯形如下图所示.梯形的第一行有m 个数字.从梯形的顶部的m 个数字开 ...

  5. Libre 6004 「网络流 24 题」圆桌聚餐(网络流,最大流)

    Libre 6004 「网络流 24 题」圆桌聚餐(网络流,最大流) Description 假设有来自n个不同单位的代表参加一次国际会议.每个单位的代表数分别为 ri.会议餐厅共有m张餐桌,每张餐桌 ...

  6. Libre 6003 「网络流 24 题」魔术球 (网络流,最大流)

    Libre 6003 「网络流 24 题」魔术球 (网络流,最大流) Description 假设有n根柱子,现要按下述规则在这n根柱子中依次放入编号为 1,2,3,4......的球. (1)每次只 ...

  7. LibreOJ #6013. 「网络流 24 题」负载平衡 最小费用最大流 供应平衡问题

    #6013. 「网络流 24 题」负载平衡 内存限制:256 MiB时间限制:1000 ms标准输入输出 题目类型:传统评测方式:文本比较 上传者: 匿名 提交提交记录统计讨论测试数据   题目描述 ...

  8. 【刷题】LOJ 6001 「网络流 24 题」太空飞行计划

    题目描述 W 教授正在为国家航天中心计划一系列的太空飞行.每次太空飞行可进行一系列商业性实验而获取利润.现已确定了一个可供选择的实验集合 \(E = \{ E_1, E_2, \cdots, E_m ...

  9. LibreOJ #6001. 「网络流 24 题」太空飞行计划

    \(\quad\) 与网络流有关的最值有三个:最大流,最小费用,最小割.这道题是最小割.想了好久,终于想明白最小割应该怎么用. \(\quad\) 先找出矛盾的事物.在这道题中,两件事是矛盾的:做实验 ...

随机推荐

  1. linux下的tar命令详解

    通过SSH访问服务器,难免会要用到压缩,解压缩,打包,解包等,这时候tar命令就是是必不可少的一个功能强大的工具.linux中最流行的tar是麻雀虽小,五脏俱全,功能强大. tar命令可以为linux ...

  2. python面试题(四)

    一.数据类型 1.字典 1.1 现有字典 dict={‘a’:24,‘g’:52,‘i’:12,‘k’:33}请按字典中的 value 值进行排序? sorted(dict.items(),key=l ...

  3. Js_特效II

    字号缩放 让文字大点,让更多的用户看的更清楚.(也可以把字体变为百分比来实现)<script type="text/javascript">  function doZ ...

  4. 简单模拟flume

    NetCat方式: 远程访问的方式进行消息传递 配置一个Agent,主要配置三个组件: source, channel, sink 上图中为什么channel会带s,变成channels? 可以绑定多 ...

  5. 【Unity Shader】从NDC(归一化的设备坐标)坐标转换到世界坐标的数学原理

    从NDC(归一化的设备坐标)坐标转换到世界坐标要点 参考资料 How to go from device coordinates back to worldspace http://feepingcr ...

  6. "Regressing Robust and Discriminative 3D Morphable Models with a very Deep Neural Network" 解读

    简介:这是一篇17年的CVPR,作者提出使用现有的人脸识别深度神经网络Resnet101来得到一个具有鲁棒性的人脸模型. 原文链接:https://www.researchgate.net/publi ...

  7. Go实现Pow工作量证明

    之前使用python编写了一段代码实现了工作量证明机制,近期由于参与以太坊智能合约开发钱包的工作接触到golang语言,所以借此以go来实现Pow(Proof of work). 实现代码如下: // ...

  8. 微软职位内部推荐-Senior Software Engineer_HPC

    微软近期Open的职位: Job Title: Senior Software Engineer_HPC Location: Shanghai, China Are you passionate ab ...

  9. centos上部署mysql

    本文记录整个安装的过程和跳进的坑,大家预祝我能从坑里爬出来吧 当前系统版本 开始我们的安装: 在安装之前查阅了部分资料,大体安装流程 yum -y install mysql yum -y insta ...

  10. ElasticSearch 2 (5) - Document APIs

    ElasticSearch 2.1.1 (5) - Document APIs This section describes the following CRUD APIs: Single docu ...