链接:

https://vjudge.net/problem/POJ-2516

题意:

Dearboy, a goods victualer, now comes to a big problem, and he needs your help. In his sale area there are N shopkeepers (marked from 1 to N) which stocks goods from him.Dearboy has M supply places (marked from 1 to M), each provides K different kinds of goods (marked from 1 to K). Once shopkeepers order goods, Dearboy should arrange which supply place provide how much amount of goods to shopkeepers to cut down the total cost of transport.

It's known that the cost to transport one unit goods for different kinds from different supply places to different shopkeepers may be different. Given each supply places' storage of K kinds of goods, N shopkeepers' order of K kinds of goods and the cost to transport goods for different kinds from different supply places to different shopkeepers, you should tell how to arrange the goods supply to minimize the total cost of transport.

思路:

建图, 但是不能对每个商品同时建图,每个商品矩阵分别建图,同时不满足条件就不要跑费用流了..会T.

代码:

#include <iostream>
#include <cstdio>
#include <cstring>
#include <vector>
//#include <memory.h>
#include <queue>
#include <set>
#include <map>
#include <algorithm>
#include <math.h>
#include <stack>
#include <string> #define MINF 0x3f3f3f3f
using namespace std;
typedef long long LL; const int MAXN = 50+10;
const int INF = 1e9; struct Edge
{
int from, to, flow, cap, cost;
Edge(int from, int to, int flow, int cap, int cost)
{
this->from = from;
this->to = to;
this->flow = flow;
this->cap = cap;
this->cost = cost;
}
}; vector<Edge> edges;
vector<int> G[MAXN*MAXN*MAXN];
int Sh[MAXN][MAXN];
int Wo[MAXN][MAXN];
int SumN[MAXN];
int a[MAXN*MAXN];
int Vis[MAXN*MAXN*MAXN], Dis[MAXN*MAXN*MAXN], Pre[MAXN*MAXN*MAXN];
int n, m, k;
int s, t; void AddEdge(int from, int to, int cap, int cost)
{
edges.push_back(Edge(from, to, 0, cap, cost));
edges.push_back(Edge(to, from, 0, 0, -cost));
int len = edges.size();
G[from].push_back(len-2);
G[to].push_back(len-1);
} bool SPFA()
{
memset(Dis, MINF, sizeof(Dis));
memset(Vis, 0, sizeof(Vis));
queue<int> que;
Dis[s] = 0;
Vis[s] = 1;
que.push(s);
a[s] = INF;
while (!que.empty())
{
// for (int i = s;i <= t;i++)
// cout << Dis[i] << ' ' ;
// cout << endl;
int u = que.front();
// cout << u << endl;
que.pop();
Vis[u] = 0;
for (int i = 0;i < G[u].size();i++)
{
Edge &e = edges[G[u][i]];
if (e.cap > e.flow && Dis[e.to] > Dis[u]+e.cost)
{
Dis[e.to] = Dis[u]+e.cost;
Pre[e.to] = G[u][i];
a[e.to] = min(a[u], e.cap-e.flow);
if (!Vis[e.to])
{
que.push(e.to);
Vis[e.to] = 1;
}
}
}
}
if (Dis[t] != MINF)
return true;
return false;
} int CostFlow(int &Flow)
{
int cost = 0;
while (SPFA())
{
// cout << 1 << endl;
// int Min = INF;
// for (int i = t;i != s;i = edges[Pre[i]].from)
// Min = min(Min, edges[Pre[i]].cap-edges[Pre[i]].flow);
// cout << Min << endl;
for (int i = t;i != s;i = edges[Pre[i]].from)
{
edges[Pre[i]].flow += a[t];
edges[Pre[i]^1].flow -= a[t];
// Edge &e = edges[Pre[i]], &ee = edges[Pre[i]^1];
// cout << e.from << ' ' << e.to << ' ' << e.flow << ' ' << e.cap << endl;
// cout << ee.from << ' ' << ee.to << ' ' << ee.flow << ' ' << ee.cap << endl;
// cout << endl;
}
cost += a[t]*Dis[t];
Flow += a[t];
}
return cost;
} void Init()
{
for (int i = 0;i <= n+m+1;i++)
G[i].clear();
edges.clear();
} int main()
{
// ios::sync_with_stdio(false);
// cin.tie(0);
while (~scanf("%d %d %d", &n, &m, &k) && (n+m+k))
{
s = 0, t = n+m+1;
for (int i = 1;i <= n;i++)
{
for (int j = 1;j <= k;j++)
scanf("%d", &Sh[i][j]);
}
memset(SumN, 0, sizeof(SumN));
for (int i = 1;i <= m;i++)
{
for (int j = 1;j <= k;j++)
scanf("%d", &Wo[i][j]), SumN[j] += Wo[i][j];
}
int v;
//shop = n*k
//wo = n*k+m*k
int res = 0, sumflow = 0;
bool ok = true;
for (int i = 1;i <= k;i++)
{
Init();
int tmp = 0;
for (int j = 1;j <= n;j++)
{
AddEdge(s, j, Sh[j][i], 0);
tmp += Sh[j][i];
}
if (tmp > SumN[i])
ok = false;
for (int j = 1;j <= n;j++)
{
for (int z = 1;z <= m;z++)
{
scanf("%d", &v);
AddEdge(j, n+z, INF, v);
}
}
for (int j = 1;j <= m;j++)
AddEdge(n+j, t, Wo[j][i], 0);
if (ok)
res += CostFlow(sumflow);
}
if (!ok)
puts("-1");
else
printf("%d\n", res);
} return 0;
}

最新文章

  1. a0=1、a1=1、a2=a1+a0、a3=a2+a1,以此类推,请写代码用递归算出a30?
  2. EChart使用简单介绍
  3. Windows Phone 8.1 Update1 支持中文“小娜”及开发者模拟器更新
  4. zabbix如何实现微信报警 转载
  5. C++ Stacks(堆栈)
  6. 组件接口(API)设计指南[5]-最后的思考
  7. python3 UnicodeEncodeError: &#39;gbk&#39; codec can&#39;t encode character &#39;\uff70&#39; in position 75267: illegal multibyte sequence
  8. Hibernate update 和 merge 、saveOrUpdate的区别
  9. JS和CSS交互的方法
  10. OpenCV3编程入门笔记(一)
  11. Netty入门教程——认识Netty
  12. Codeforces 285C - Building Permutation
  13. linux命令系列 grep
  14. Activity相关知识点总结
  15. markdown 语法规则
  16. 怎么使用 ab.exe 测试多个url。 how to use ab.exe test many url
  17. 2014年辛星解读Javascript之DOM之事件及其绑定
  18. svn lock 锁定文件
  19. LeetCode——Find Largest Value in Each Tree Row
  20. ant-design表单处理和常用方法及自定义验证

热门文章

  1. 测开之路一百五十三:ajax之load、get、ajax在项目中的体现
  2. 中国MOOC_零基础学Java语言_第7周 函数_1分解质因数
  3. 动画演示 Delphi 2007 IDE 功能[2] - 定义变量
  4. jupyter 服务器安装随笔
  5. python下对文件的操作(非目录)
  6. Bean的构造器注入和setter注入
  7. [Git] 021 来一颗“恶魔果实”?
  8. 全新一台node节点加入到集群中
  9. TApplication,TForm,TControl,TComponent,TWinControl研究(博客索引)good
  10. 源码编译Redis Desktop Manager | 懒人屋