网络流当前弧度优化相关问题求助!
  • 板块学术版
  • 楼主Gszfzsf
  • 当前回复8
  • 已保存回复9
  • 发布时间2025/7/24 15:28
  • 上次更新2025/7/24 18:56:09
查看原帖
网络流当前弧度优化相关问题求助!
1582565
Gszfzsf楼主2025/7/24 15:28

今天重写网络流时突然发现跑的特别慢( Link 1.02s)。

回去看了之前的代码(Link 67ms)。

发现写的完全一致,除了当前弧优化的实现方式:

慢的:

for(int &i=now[dq];i&∑i=Edge[i].nxt){
		int yy=Edge[i].y;
		if(Edge[i].v>0 && dis[yy]==dis[dq]+1){
			k=DFS(yy,min(sum,Edge[i].v));
			if(k==0) dis[yy]=INF;
			Edge[i].v-=k; sum-=k;
			Edge[i^1].v+=k; res+=k;
		}
	}return res;

快的:

for(int i=now[dq];i&∑i=Edge[i].nxt){
		int yy=Edge[i].y; now[dq]=i;
		if(Edge[i].v>0 && dis[yy]==dis[dq]+1){
			k=DFS(yy,min(sum,Edge[i].v));
			if(k==0) dis[yy]=INF;
			Edge[i].v-=k; sum-=k;
			Edge[i^1].v+=k; res+=k;
		}
	}return res;

不难发现,慢的使用了 & 符号直接更新了 nownow 数组,而快的在进循环时显式更新,虽然看起来差不多,但在时间上相差了接近20倍。可是我已经用这种“慢”的方法闯过了好多网络流了,而且不少题解里的大佬也用的这种方法,怎么模板题里面相差这么多???(看起来就像没写一样…

不清楚为什么会有这种情况发生,取址的方法是错误的吗,求大佬解释……

完整代码在下面,已经控制变量法验证了二者只有上述地方不同,所以只放慢的:

#include<bits/stdc++.h>
using namespace std;
#define int long long
const int INF = 0x3f3f3f3f3f3f3f3f;
const int N = 207;
const int M = 5007;
int ans;
int n,m;
int st,ed;
int now[N];
int dis[N];
int Link[N],l=1;
struct edge{int y,v,nxt;}Edge[M<<2];
inline void Insert(int x,int y,int v){
	l++;
	Edge[l].nxt=Link[x];
	Link[x]=l;
	Edge[l].y=y;
	Edge[l].v=v;
}
bool BFS(){
	for(int i=1;i<=n;i++) dis[i]=INF;
	queue <int> Q; Q.push(st);
	dis[st]=0; now[st]=Link[st];
	while(Q.empty()!=true){
		int dq=Q.front(); Q.pop();
		for(int i=Link[dq];i;i=Edge[i].nxt){
			int yy=Edge[i].y;
			if(Edge[i].v>0 && dis[yy]==INF){
				Q.push(yy);
				now[yy]=Link[yy];
				dis[yy]=dis[dq]+1;
				if(yy==ed) return true;
			}
		}
	}return false;
}
int DFS(int dq,int sum){
	if(dq==ed) return sum;
	int k,res=0;
	for(int &i=now[dq];i&&sum;i=Edge[i].nxt){
		int yy=Edge[i].y;
		if(Edge[i].v>0 && dis[yy]==dis[dq]+1){
			k=DFS(yy,min(sum,Edge[i].v));
			if(k==0) dis[yy]=INF;
			Edge[i].v-=k; sum-=k;
			Edge[i^1].v+=k; res+=k;
		}
	}return res;
}
signed main(){
	ios::sync_with_stdio(0);
	cin.tie(0); cout.tie(0);
	cin>>n>>m>>st>>ed;
	for(int i=1;i<=m;i++){
		int x,y,v;
		cin>>x>>y>>v;
		Insert(x,y,v);
		Insert(y,x,0);
	}while(BFS()) ans+=DFS(st,INF);
	cout<<ans;
	return 0;
}
2025/7/24 15:28
加载中...