【题解】Catering World Finals 2015 上下界费用流
2017-12-28 20:25
429 查看
Prelude
传送到Codeforces:0.0Solution
板子题,在这里贴个板子。这题面是smg?题面中有说每个点只能经过一次吗?是我瞎了吗?
因为这WA on test 27一个小时,烦死了,浪费时间。
Code
#include <cstring> #include <algorithm> #include <cstdio> #include <queue> #include <cassert> using namespace std; const int MAXN = 1000; const int MAXM = 100000; const int INF = 0x3f3f3f3f; int _w; int read() { int x; _w = scanf( "%d", &x ); return x; } namespace MCMF { struct Edge { int u, v, c, f, w; Edge() {} Edge( int u, int v, int c, int f, int w ): u(u), v(v), c(c), f(f), w(w) {} }; int n, m, s, t; int head[MAXN], nxt[MAXM]; Edge edge[MAXM]; void init( int _n ) { n = _n, m = 0; for( int i = 0; i < n; ++i ) head[i] = -1; } void adde( int u, int v, int c, int w ) { edge[m] = Edge(u, v, c, 0, w); nxt[m] = head[u], head[u] = m++; edge[m] = Edge(v, u, 0, 0, -w); nxt[m] = head[v], head[v] = m++; } queue<int> q; int dis[MAXN], inq[MAXN], res[MAXN], from[MAXN]; bool spfa() { for( int i = 0; i < n; ++i ) dis[i] = INF, inq[i] = 0; dis[s] = 0, inq[s] = 1, q.push(s), res[s] = INF; while( !q.empty() ) { int u = q.front(); q.pop(); inq[u] = 0; for( int i = head[u]; ~i; i = nxt[i] ) { const Edge &e = edge[i]; if( e.c > e.f && dis[u] + e.w < dis[e.v] ) { dis[e.v] = dis[u] + e.w; from[e.v] = i; res[e.v] = min( res[u], e.c-e.f ); if( !inq[e.v] ) inq[e.v] = 1, q.push(e.v); } } } return dis[t] != INF; } void augment() { int f = res[t], u = t; while( u != s ) { int i = from[u]; edge[i].f += f; edge[i^1].f -= f; u = edge[i].u; } } int solve( int _s, int _t ) { s = _s, t = _t; int cost = 0; while( spfa() ) { cost += res[t] * dis[t]; augment(); } return cost; } } int n, k, g[MAXN][MAXN]; int s, t, ss, tt, nid; int in[MAXN], out[MAXN]; void adde( int u, int v, int l, int r, int w ) { MCMF::adde(ss, v, l, 0); MCMF::adde(u, tt, l, 0); MCMF::adde(u, v, r-l, w); } void solve() { s = nid++, t = nid++, ss = nid++, tt = nid++; for( int i = 1; i <= n; ++i ) in[i] = nid++, out[i] = nid++; MCMF::init(nid); adde(t, s, 0, INF, 0); adde(s, out[1], 0, k, 0); for( int i = 2; i <= n; ++i ) { adde(out[i], t, 0, INF, 0); adde(in[i], out[i], 1, 1, 0); // 每个点只能经过一次 } for( int i = 1; i <= n; ++i ) for( int j = i+1; j <= n; ++j ) adde(out[i], in[j], 0, INF, g[i][j]); printf( "%d\n", MCMF::solve(ss, tt) ); } int main() { n = read()+1, k = read(); for( int i = 1; i <= n; ++i ) for( int j = i+1; j <= n; ++j ) g[i][j] = read(); solve(); return 0; }
相关文章推荐
- [BZOJ4108][Wf2015]Catering(有源汇有上下界的费用流)
- BZOJ 4108: [Wf2015]Catering [上下界费用流]
- 【bzoj4108】[Wf2015]Catering 上下界费用流
- 【bzoj4108】[Wf2015]Catering 有上下界费用流
- bzoj 4108: [Wf2015]Catering|带上下界最小费用可行流
- bzoj 4108: [Wf2015]Catering (有源汇有上下界的费用流)
- 【BZOJ4108】[Wf2015]Catering 有上下界费用流
- UVALive 7152 Catering (有上下界的)费用流
- 【线段树优化建图+费用流Spfa增广】BZOJ4276(ONTAK2015)[Bajtman i Okrągły Robin]题解
- [BZOJ2055]80人环游世界(有源汇有上下界的费用流)
- 【树形DP】(2015)第六届蓝桥杯省赛 C/C++ B组 题解(第十题)
- BZOJ3994:[SDOI2015]约数个数和——题解
- 【bzoj3876】【AHOI2014】【支线剧情】【有上下界的费用流】
- BZOJ 3876 AHOI 2014 支线剧情 有下界有源汇的费用流
- BZOJ4004:[JLOI2015]装备购买——题解
- BZOJ4104:[Thu Summer Camp 2015]解密运算——题解
- Codeforces Gym 101190 NEERC 16 .D Delight for a Cat (上下界的费用流)
- bzoj3876[AHOI2014]支线剧情(有上下界的费用流)
- 【题解】亚瑟王 HNOI 2015 BZOJ 4008 概率 期望 动态规划
- 网络流模板(费用流/可行流/上下界)