社区讨论

【求助】为什么网络流只有40分

P2055[ZJOI2009] 假期的宿舍参与者 1已保存回复 0

讨论操作

快速查看讨论及其快照的属性,并进行相关操作。

当前回复
0 条
当前快照
1 份
快照标识符
@mi6o8mid
此快照首次捕获于
2025/11/20 08:06
4 个月前
此快照最后确认于
2025/11/20 08:06
4 个月前
查看原帖
网络流算法,用[1,n]内的数代表学生,床拆点,回家的学生直接连到汇点,每个有床位的人和自己的床连,为啥40分,求大神纠错
CPP
#include<iostream>
#include<cstdio>
#include<cstring>
#include<queue>
#include<vector>
#define MAXN 1000
using namespace std;
const int INF=1<<30;
inline int min(int a,int b){return a<b?a:b;}
inline int read(){
	int out=0;
	char c=getchar();
	while(c<48||c>57) c=getchar();
	while(c<=57&&c>=48){
		out=(out<<1)+(out<<3)+c-48;
		c=getchar();
	}
	return out;
}
void write(int x){
	if(x>9) write(x/10);
	putchar(x%10+48);
}
struct Edge{int u,v,cap,flow;};
struct dinic{
	int n,m,s,t;
	vector<Edge>edge;
	vector<int>node[MAXN];
	int dis[MAXN],cur[MAXN];
	void init(){
		for(int i=1;i<=n;++i) node[i].clear();
		edge.clear();
	}
	void addedge(int u,int v,int cap){
		edge.push_back(Edge{u,v,cap,0});
		edge.push_back(Edge{v,u,0,0});
		int temp=edge.size();
		node[u].push_back(temp-2);
		node[v].push_back(temp-1);
	}
	bool bfs(){
		static bool vis[MAXN];
		memset(vis,0,sizeof(vis));
		queue<int>q;
		q.push(s);
		vis[s]=1;
		dis[s]=0;
		while(!q.empty()){
			int u=q.front();
			q.pop();
			for(int i=0;i<node[u].size();++i){
				Edge &e=edge[node[u][i]];
				if(!vis[e.v]&&e.cap>e.flow){
					vis[e.v]=1;
					q.push(e.v);
					dis[e.v]=dis[u]+1;
				}
			}
		}
		return vis[t];
	}
	int dfs(int u,int a){
		if(u==t||!a) return a;
		int flow=0,f;
		for(int& i=cur[u];i<node[u].size();++i){
			Edge& e=edge[node[u][i]];
			if(dis[u]+1==dis[e.v]&&(f=dfs(e.v,min(a,e.cap-e.flow)))>0){
				flow+=f;
				a-=f;
				e.flow+=f;
				edge[node[u][i]^1].flow-=flow;
				if(!a) break;
			}
		}
		return flow;
	}
	int maxflow(){
		int flow=0;
		while(bfs()){
			memset(cur,0,sizeof(cur));
			flow+=dfs(s,INF);
		}
		return flow;
	}
}G;
bool sch[MAXN];
int home[MAXN],rel[MAXN][MAXN];
void init(){
	int n=read(); 
	G.n=n;
	G.init();
	for(int i=1;i<=n;++i) sch[i]=read();
	for(int i=1;i<=n;++i) home[i]=read();
	for(int i=1;i<=n;++i)
		for(int j=1;j<=n;++j) rel[i][j]=read();
	G.s=0;
	G.t=n*3+1;
	for(int i=1;i<=n;++i){
		G.addedge(0,i,1);
		G.addedge(i+n,i+2*n,1);
		G.addedge(i+n*2,G.t,1);
	}
	for(int i=1;i<=n;++i){
		if(sch[i]){
			G.addedge(i,i+n,1);
			if(home[i]) G.addedge(i,G.t,1);
		}
	}
	for(int i=1;i<=n;++i){
		for(int j=1;j<=n;++j){
			if(rel[i][j]&&sch[j]) G.addedge(i,j+n,1);
		}
	}
}
int main(){
	int T=read();
	while(T--){
		init();
		int ans=G.maxflow();
		if(ans>=G.n){
			putchar(94);
			putchar(95);
			putchar(94);
		}
		else{
			putchar(84);
			putchar(95);
			putchar(84);
		}
		putchar(10);
	}
	return 0;
}

回复

0 条回复,欢迎继续交流。

正在加载回复...