题目描述

G 公司有 n 个沿铁路运输线环形排列的仓库,每个仓库存储的货物数量不等。如何用最少搬运量可以使 n 个仓库的库存数量相同。搬运货物时,只能在相邻的仓库之间搬运。

输入输出格式

输入格式:

文件的第 1行中有 1 个正整数 n,表示有 n 个仓库。

第 2 行中有 n 个正整数,表示 n 个仓库的库存量。

输出格式:

输出最少搬运量。

输入输出样例

输入样例#1: 复制

5
17 9 14 16 4
输出样例#1: 复制

11

说明

1≤n≤100

题解:

计算平均每个点的量,然后看当前点是流入还是流出,流出与超级源点连接,流入与汇点相连,将每个点拆分点两个点xi,yi。xi 与yi相连流量INF,费用为0,然后每个点与相邻两个点连接,xi-xi-1,yi-yi+1,相连接

#include<bits/stdc++.h>
using namespace std;
#define LL long long
const int MAXN= 20000+10;
const int INF=0x3f3f3f3;
struct Edge{
int from,to,cap,flow,cost;
Edge(int u,int v, int c,int f ,int w):from(u),to(v),cap(c),flow(f),cost(w)
{}
};
struct MCMF
{
int n,m;
vector<Edge>edges;
vector<int>G[MAXN];
int inq[MAXN];
int d[MAXN];
int p[MAXN];
int a[MAXN];
void init(int n) {
this->n=n;
for (int i=0;i<=n;i++)G[i].clear();
edges.clear();
}
void AddEdge(int from, int to,int cap,int cost)
{
edges.push_back(Edge(from,to,cap,0,cost));
edges.push_back(Edge(to,from,0,0,-cost));
m=edges.size();
G[from].push_back(m-2);
G[to].push_back(m-1);
}
bool BellmanFord(int s,int t,int &flow,long long &cost){
for(int i=0;i<=n;i++)d[i]=INT_MAX;
memset(inq,0, sizeof(inq));
d[s]=0;inq[s]=1;p[s]=0;a[s]=INT_MAX;
queue<int >Q;
Q.push(s);
while(!Q.empty()){
int u=Q.front();Q.pop();
inq[u]=0;
int ll=G[u].size();
for (int i = 0; i <ll ; ++i) {
Edge& e=edges[G[u][i]];
if(e.cap>e.flow&&d[e.to]>d[u]+e.cost){
d[e.to]=d[u]+e.cost;
p[e.to]=G[u][i];
a[e.to]=min(a[u],e.cap-e.flow);
if(!inq[e.to]){Q.push(e.to);inq[e.to]=1;}
}
}
}
if(d[t]==INT_MAX) return false;
flow+=a[t];
cost+=(long long)d[t]*(long long )a[t];
for (int u = t; u !=s ; u=edges[p[u]].from) {
edges[p[u]].flow+=a[t];
edges[p[u]^1].flow-=a[t];
}
return true;
}
int MincostMaxflow(int s,int t,long long &cost){
int flow=0;cost=0;
while(BellmanFord(s, t, flow, cost));
return flow;
} };
int d[200],xx[200];
int main()
{
int n,sum=0;
scanf("%d\n",&n);
for (int i = 1; i <=n ; ++i) {
scanf("%d",&xx[i]);
sum+=xx[i];
}
sum=sum/n;
for (int i = 1; i <=n ; ++i) {
d[i]=xx[i]-sum;
}
MCMF M;
M.init(n+n+2);
for (int i = 1; i <=n ; ++i) {
if(d[i]>0)
{
M.AddEdge(0,i,d[i],0);
}
if(d[i]<0)
{
M.AddEdge(i+n,n+n+1,-d[i],0);
}
if(i==1)
{
M.AddEdge(1,n,INF,1);
M.AddEdge(1,n+n,INF,1);
} else
{
M.AddEdge(i,i-1,INF,1);
M.AddEdge(i,n+i-1,INF,1);
}
if(i==n)
{
M.AddEdge(n,1,INF,1);
M.AddEdge(n,n+1,INF,1);
} else
{
M.AddEdge(i,i+1,INF,1);
M.AddEdge(i,i+1+n,INF,1);
}
}
LL cost=0;
M.MincostMaxflow(0,n+n+1,cost);
printf("%lld\n",cost);
return 0;
}

  

洛谷P4016 负载平衡问题的更多相关文章

  1. 洛谷 P4016负载平衡问题【费用流】题解+AC代码

    洛谷 P4016负载平衡问题 P4014 分配问题[费用流]题解+AC代码 负载平衡问题 题目描述 GG 公司有n个沿铁路运输线环形排列的仓库,每个仓库存储的货物数量不等.如何用最少搬运量可以使 n ...

  2. (洛谷P2512||bzoj1045) [HAOI2008]糖果传递 || 洛谷P4016 负载平衡问题 || UVA11300 Spreading the Wealth || (洛谷P3156||bzoj3293) [CQOI2011]分金币

    bzoj1045 洛谷P4016 洛谷P2512 bzoj3293 洛谷P3156 题解:https://www.luogu.org/blog/LittleRewriter/solution-p251 ...

  3. 洛谷P4016负载平衡

    题目 负载平衡问题是一个比较经典的网络流问题,但是该问题还有一个数学贪心法. 所以做这个题前,其实可以做一下均分纸牌问题. 均分纸牌问题 均分纸牌问题可以说是作为贪心的入门题. 做法 首先我们应当把原 ...

  4. 洛谷 [P4016] 负载平衡问题

    贪心做法 第一眼看见觉得和均分纸牌差不多,然而因为这是环形的,并不能用均分纸牌的方法做,但是均分纸牌的思想仍然适用 首先我们假设平均数为sum1. 那么对于第1个人,我们假设他给第N个人K个糖果, 第 ...

  5. 洛谷P4016 负载平衡问题(费用流)

    传送门 嗯……完全不会……不过题解似乎讲的挺清楚…… 考虑一下,每一个仓库最终肯定都是平均数,所以数量大于平均数的可以往外运,小于平均数的要从别的地方运进来 考虑建一个超级源$S$和超级汇$T$,并把 ...

  6. 洛谷 P4016 负载平衡问题 【最小费用最大流】

    求出平均数sum,对于大于sum的点连接(s,i,a[i]-sum,0),表示这个点可以流出多余的部分,对于小于sum的点连接(i,t,sum-a[i],0)表示这个点可以接受少的部分,然后每个点向相 ...

  7. 洛谷P4016 负载平衡问题(最小费用最大流)

    题目描述 GG 公司有 nn 个沿铁路运输线环形排列的仓库,每个仓库存储的货物数量不等.如何用最少搬运量可以使 nn 个仓库的库存数量相同.搬运货物时,只能在相邻的仓库之间搬运. 输入输出格式 输入格 ...

  8. 洛谷P4016 负载平衡问题 费用流

    这道题还是很好的. 考察了选手对网络流的理解. 首先,任意两个相邻点之间的运货量时没有限制的. 我们可以将相邻点之间的流量建为无限大,单位费用设为 1,代表运输一个货物需耗费一个代价. 由于题目要求最 ...

  9. 『题解』洛谷P4016 负载平衡问题

    title: categories: tags: - mathjax: true --- Problem Portal Portal1:Luogu Portal2: LibreOJ Descripti ...

随机推荐

  1. Java 实现斐波那契数列

    public class Fibonacci { private static int getFibo(int i) { if (i == 1 || i == 2) return 1; else re ...

  2. webpack前言:前端模块系统的演进

    前端开发和其他开发工作的主要区别,首先是前端是基于多语言.多层次的编码和组织工作,其次前端产品的交付是基于浏览器,这些资源是通过增量加载的方式运行到浏览器端,如何在开发环境组织好这些碎片化的代码和资源 ...

  3. Android(java)学习笔记9:JDK5之后的Lock锁的概述和使用

    1. Lock锁的概述: java.util.concurrent.locks,接口Lock 首先Lock是一个接口,Lock实现提供了比使用synchronized方法 和 同步代码块更为广泛的锁定 ...

  4. Android(java)学习笔记49:通过反射获取私有构造方法并且使用

    1. 反射获取私有构造方法并且使用: (1)获取字节码文件.class对象:          Class c = Class.forName("cn.itcast_01.Person&qu ...

  5. 【[CTSC2000]冰原探险】

    noip前练一下码力还是非常有前途的 这道题本来就是想写个大暴力弃疗的,所以直接强上暴力浑身舒爽 结果发现要不是判重的时候脑残了,就能\(A\)了 没什么好说的呀,就是每一次都暴力\(O(n)\)往上 ...

  6. 【转】netstat 命令当中的内部地址和外部地址分别代表的是什么?

    RT,用自己的话解释,不要搬网上的内容.尽量可以简洁,谢谢 2015-03-07 17:41 提问者采纳   网络连接是有2方参与,自己就是“内部地址”,别人就是“外部地址”,就这么简洁. 再举个例子 ...

  7. 【luoguP1996】【luogu-original】约瑟夫问题

    先来看题目: P1996 约瑟夫问题 题目背景 约瑟夫是一个无聊的人!!! 题目描述 n个人(n<=100)围成一圈,从第一个人开始报数,数到m的人出列,再由下一个人重新从1开始报数,数到m的人 ...

  8. Android学习笔记_78_ Android开发中使用软引用和弱引用防止内存溢出

    在<Effective Java 2nd Edition>中,第6条“消除过期的对象引用”提到,虽然Java有 垃圾回收机制,但是只要是自己管理的内存,就应该警惕内存泄露的问题,例如的对象 ...

  9. HDU 1221 Rectangle and Circle(判断圆和矩形是不是相交)

    传送门: http://acm.hdu.edu.cn/showproblem.php?pid=1221 Rectangle and Circle Time Limit: 2000/1000 MS (J ...

  10. ng-repeat 指令(带有数组)

    <!DOCTYPE html><html><head><meta http-equiv="Content-Type" content=&q ...