题意:

求最大流

思路:

\(1e5\)条边,偷了一个超长的\(HLPP\)板子。复杂度\(n^2 \sqrt{m}\)。但通常在随机情况下并没有isap快。

板子:

template<class T = int>
struct HLPP{
const int MAXN = 1e5 + 5;
const T INF = 0x3f3f3f3f;
struct edge{
int to, rev;
T f;
};
vector<edge> adj[maxn];
deque<int> lst[maxn];
vector<int> gap[maxn];
T excess[maxn];
int highest, height[maxn], cnt[maxn], ptr[maxn], work, N; void addEdge(int u, int v, int f, bool isdirected = true){
adj[u].push_back({v, adj[v].size(), f});
adj[v].push_back({u, adj[u].size() - 1, isdirected? 0 : f});
} void clear(int n){
N = n;
for(int i = 0; i <= n; i++){
adj[i].clear(), lst[i].clear();
gap[i].clear();
}
} void upHeight(int v, int nh){
++work;
if(height[v] != N) --cnt[height[v]];
height[v] = nh;
if(nh == N) return;
cnt[nh]++, highest = nh;
gap[nh].push_back(v);
if(excess[v] > 0){
lst[nh].push_back(v);
++ptr[nh];
}
} void glovalRelabel(int s, int t){
work = 0;
fill(height, height + N + 1, N);
fill(cnt, cnt + N + 1, 0);
for(int i = 0; i <= highest; i++){
lst[i].clear();
gap[i].clear();
ptr[i] = 0;
}
height[t] = 0;
queue<int> q({t});
while(!q.empty()){
int v = q.front();
q.pop();
for(auto &e : adj[v])
if(height[e.to] == N && adj[e.to][e.rev].f > 0){
q.push(e.to);
upHeight(e.to, height[v] + 1);
}
highest = height[v];
}
}
void push(int v, edge& e){
if(excess[e.to] == 0){
lst[height[e.to]].push_back(e.to);
++ptr[height[e.to]];
}
T df = min(excess[v], e.f);
e.f -= df;
adj[e.to][e.rev].f += df;
excess[v] -= df;
excess[e.to] += df;
}
void discharge(int v){
int nh = N;
for(auto &e : adj[v]){
if(e.f > 0){
if(height[v] == height[e.to] + 1){
push(v, e);
if(excess[v] <= 0) return;
}
else{
nh = min(nh, height[e.to] + 1);
}
}
}
if(cnt[height[v]] > 1){
upHeight(v, nh);
}
else{
for(int i = height[v]; i < N; i++){
for(auto j : gap[i]) upHeight(j, N);
gap[i].clear(); ptr[i] = 0;
}
}
} T hlpp(int s, int t){
fill(excess, excess + N + 1, 0);
excess[s] = INF, excess[t] = -INF;
glovalRelabel(s, t);
for(auto &e : adj[s]) push(s, e);
for(; highest >= 0; -- highest){
while(lst[highest].size()){
int v = lst[highest].back();
lst[highest].pop_back();
discharge(v);
if(work > 4 * N) glovalRelabel(s, t);
}
}
return excess[t] + INF;
} }; int read() {
int f = 1, x = 0; char ch = getchar();
while(! isdigit(ch)) {if(ch == '-' ) f = -f; ch = getchar();}
while(isdigit(ch)) {x = x * 10 + ch - '0'; ch = getchar();}
return x * f;
} HLPP<int> hlpp; //hlpp.clear(n)

代码:

#include <iostream>
#include <algorithm>
#include <cstring>
#include <cstdlib>
#include <string>
#include <cstdio>
#include <queue>
#define isdigit(a) (a>='0' && a<='9')
typedef long long LL;
using namespace std;
const int inf = 0x3f3f3f3f;
const int maxn = 2e5+5; template<class T = int>
struct HLPP{
const int MAXN = 1e5 + 5;
const T INF = 0x3f3f3f3f;
struct edge{
int to, rev;
T f;
};
vector<edge> adj[maxn];
deque<int> lst[maxn];
vector<int> gap[maxn];
T excess[maxn];
int highest, height[maxn], cnt[maxn], ptr[maxn], work, N; void addEdge(int u, int v, int f, bool isdirected = true){
adj[u].push_back({v, adj[v].size(), f});
adj[v].push_back({u, adj[u].size() - 1, isdirected? 0 : f});
} void clear(int n){
N = n;
for(int i = 0; i <= n; i++){
adj[i].clear(), lst[i].clear();
gap[i].clear();
}
} void upHeight(int v, int nh){
++work;
if(height[v] != N) --cnt[height[v]];
height[v] = nh;
if(nh == N) return;
cnt[nh]++, highest = nh;
gap[nh].push_back(v);
if(excess[v] > 0){
lst[nh].push_back(v);
++ptr[nh];
}
} void glovalRelabel(int s, int t){
work = 0;
fill(height, height + N + 1, N);
fill(cnt, cnt + N + 1, 0);
for(int i = 0; i <= highest; i++){
lst[i].clear();
gap[i].clear();
ptr[i] = 0;
}
height[t] = 0;
queue<int> q({t});
while(!q.empty()){
int v = q.front();
q.pop();
for(auto &e : adj[v])
if(height[e.to] == N && adj[e.to][e.rev].f > 0){
q.push(e.to);
upHeight(e.to, height[v] + 1);
}
highest = height[v];
}
}
void push(int v, edge& e){
if(excess[e.to] == 0){
lst[height[e.to]].push_back(e.to);
++ptr[height[e.to]];
}
T df = min(excess[v], e.f);
e.f -= df;
adj[e.to][e.rev].f += df;
excess[v] -= df;
excess[e.to] += df;
}
void discharge(int v){
int nh = N;
for(auto &e : adj[v]){
if(e.f > 0){
if(height[v] == height[e.to] + 1){
push(v, e);
if(excess[v] <= 0) return;
}
else{
nh = min(nh, height[e.to] + 1);
}
}
}
if(cnt[height[v]] > 1){
upHeight(v, nh);
}
else{
for(int i = height[v]; i < N; i++){
for(auto j : gap[i]) upHeight(j, N);
gap[i].clear(); ptr[i] = 0;
}
}
} T hlpp(int s, int t){
fill(excess, excess + N + 1, 0);
excess[s] = INF, excess[t] = -INF;
glovalRelabel(s, t);
for(auto &e : adj[s]) push(s, e);
for(; highest >= 0; -- highest){
while(lst[highest].size()){
int v = lst[highest].back();
lst[highest].pop_back();
discharge(v);
if(work > 4 * N) glovalRelabel(s, t);
}
}
return excess[t] + INF;
} }; int read() {
int f = 1, x = 0; char ch = getchar();
while(! isdigit(ch)) {if(ch == '-' ) f = -f; ch = getchar();}
while(isdigit(ch)) {x = x * 10 + ch - '0'; ch = getchar();}
return x * f;
} HLPP<int> hlpp; int main() {
int T;
scanf("%d", &T);
while(T--) {
int n, m;
scanf("%d%d", &n, &m);
int x, y, s, t;
int startX = inf, endX = -inf;
for(int i = 1; i <= n; ++i) {
x = read(), y = read();
if(x < startX) s = i, startX = x;
if(x > endX) t = i, endX = x;
}
int u, v, f;
hlpp.clear(n);
for(int i = 1; i <= m; ++i) {
u = read(), v = read(), f = read();
hlpp.addEdge(u, v, f, false);
} printf("%d\n", hlpp.hlpp(s, t));
}
return 0;
}

HDU 4280 Island Transport(HLPP板子)题解的更多相关文章

  1. HDU 4280 Island Transport(网络流,最大流)

    HDU 4280 Island Transport(网络流,最大流) Description In the vast waters far far away, there are many islan ...

  2. HDU 4280 Island Transport

    Island Transport Time Limit: 10000ms Memory Limit: 65536KB This problem will be judged on HDU. Origi ...

  3. Hdu 4280 Island Transport(最大流)

    Island Transport Time Limit: 20000/10000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Other ...

  4. HDU 4280 Island Transport(无向图最大流)

    HDU 4280:http://acm.hdu.edu.cn/showproblem.php?pid=4280 题意: 比较裸的最大流题目,就是这是个无向图,并且比较卡时间. 思路: 是这样的,由于是 ...

  5. HDU 4280 Island Transport(dinic+当前弧优化)

    Island Transport Description In the vast waters far far away, there are many islands. People are liv ...

  6. HDU 4280 Island Transport(网络流)

    转载请注明出处:http://blog.csdn.net/u012860063 题目链接:pid=4280">http://acm.hdu.edu.cn/showproblem.php ...

  7. 【HDUOJ】4280 Island Transport

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=4280 题意:有n个岛屿,m条无向路,每个路给出最大允许的客流量,求从最西的那个岛屿最多能运用多少乘客到 ...

  8. HDU 1385 Minimum Transport Cost 最短路径题解

    本题就是使用Floyd算法求全部路径的最短路径,并且须要保存路径,并且更进一步须要依照字典顺序输出结果. 还是有一定难度的. Floyd有一种非常巧妙的记录数据的方法,大多都是使用这种方法记录数据的. ...

  9. HDU4280:Island Transport(最大流)

    Island Transport Time Limit: 20000/10000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Other ...

随机推荐

  1. luogu P4116 Qtree3

    题目描述 给出N个点的一棵树(N-1条边),节点有白有黑,初始全为白 有两种操作: 0 i : 改变某点的颜色(原来是黑的变白,原来是白的变黑) 1 v : 询问1到v的路径上的第一个黑点,若无,输出 ...

  2. Sentry(v20.12.1) K8S 云原生架构探索,JavaScript Enriching Events(丰富事件信息)

    系列 Sentry-Go SDK 中文实践指南 一起来刷 Sentry For Go 官方文档之 Enriching Events Snuba:Sentry 新的搜索基础设施(基于 ClickHous ...

  3. SQL Server和Oracle数据类型对应关系

    在工作中,有时会遇到跨库传输数据的情况,其中 SQL Server 和 Oracle 之间的数据传输是比较常见的情况. 因为 SQL Server 和 Oracle 的数据类型有些差异,这就要求我们在 ...

  4. Bitter.Core系列七:Bitter ORM NETCORE ORM 全网最粗暴简单易用高性能的 NETCore ORM 示例 更新删除插入

    Bitter Orm 在操作数据库增删改的时候,支持模型驱动和直接执行裸SQL 操作,示例代码如下: 一:模型驱动(增删改) /// <summary> /// 插入,删除,更新示例(模型 ...

  5. code-server Command ' ' not found

    由于通过一些特殊的方式登录linux用户后,全局变量不会自动加载,需要在 vscode 的 bash terminal手动读取 输入 source /etc/profile 或者vim ~/.bash ...

  6. 一站式入口服务|爱奇艺微服务平台 API 网关实战 原创 弹性计算团队 爱奇艺技术产品团队

    一站式入口服务|爱奇艺微服务平台 API 网关实战 原创 弹性计算团队 爱奇艺技术产品团队

  7. mysqldump 内存消耗

    MySQL :: MySQL 8.0 Reference Manual :: 4.5.4 mysqldump - A Database Backup Program https://dev.mysql ...

  8. gitignore 不起作用的解决办法 不再跟踪 让.gitignore生效,跟踪希望被跟踪的文件

    实践 # https://git-scm.com/docs/gitignore https://git-scm.com/docs/gitignore 不跟踪log目录下的所有文件,但需要保留这个文件夹 ...

  9. Map转换为格式化的YAML字符串

    yaml与java对象的互转 yaml与java对象的互转有snakeyaml <dependency> <groupId>org.yaml</groupId> & ...

  10. docker(mysql-redmine)

    一.安装docker 首先查看自己的版本,我的是centos 版本为 [root@localhost redmine]# uname -r 3.10.0-862.el7.x86_64 移除旧版本 yu ...