- 1、本文档共3页,可阅读全部内容。
- 2、原创力文档(book118)网站文档一经付费(服务费),不意味着购买了该文档的版权,仅供个人/单位学习、研究之用,不得用于商业用途,未经授权,严禁复制、发行、汇编、翻译或者网络传播等,侵权必究。
- 3、本站所有内容均由合作方或网友上传,本站不对文档的完整性、权威性及其观点立场正确性做任何保证或承诺!文档内容仅供研究参考,付费前请自行鉴别。如您付费,意味着您自己接受本站规则且自行承担风险,本站不退款、不进行额外附加服务;查看《如何避免下载的几个坑》。如果您已付费下载过本站文档,您可以点击 这里二次下载。
- 4、如文档侵犯商业秘密、侵犯著作权、侵犯人身权等,请点击“版权申诉”(推荐),也可以打举报电话:400-050-0827(电话支持时间:9:00-18:30)。
查看更多
标号法求网络最大流量
//标号法求网络最大流量
#include cstdio
#include cmath
#include cstring
#define MAXN 1000 //顶点个数最大值
#define INF 1000000 //无穷大
#define MIN(a,b) ((a)(b)?(a):(b))
struct ArcType //弧结构
{
int c, f; //容量,流量
};
ArcType Edge[MAXN][MAXN]; //邻接矩阵(每个元素为ArcType类型)
int n, m; //顶点个数和弧数
int flag[MAXN]; //顶点状态:-1-未标号,0-已标号未检查,1-已标号已检查
int prev[MAXN]; //标号的第一个分量:指明标号从哪个顶点得到,以便找出可改进量
int alpha[MAXN]; //标号的第二个分量:可改进量α
int queue[MAXN]; //相当于BFS算法中的队列
int v; //从队列里取出来的队列头元素
int qs, qe; //队列头位置,队列尾位置
int i, j; //循环变量
void ford( )
{
while( 1 ) //标号直至不存在可改进路
{
//标号前对顶点状态数组初始化
memset( flag, 0xff, sizeof(flag) ); //将3个数组各元素初始化为-1
memset( prev, 0xff, sizeof(prev) ); memset( alpha, 0xff, sizeof(alpha) );
flag[0] = 0; prev[0] = 0; alpha[0] = INF; //源点为已标号未检查顶点
qs = qe = 0;
queue[qe] = 0; qe++; //源点(顶点0)入队列
//qsqe表示队列非空, flag[n-1]==-1表示汇点未标号
while( qsqe flag[n-1]==-1 )
{
v = queue[qs]; qs++; //取出队列头顶点
for( i=0; in; i++ ) //检查顶点v的正向和反向邻接顶点
{
if( flag[i]==-1 ) //顶点i未标号
{
//正向且未满
if( Edge[v][i].cINF Edge[v][i].f Edge[v][i].c )
{
flag[i] = 0; prev[i] = v; //给顶点i标号(已标号未检查)
alpha[i] = MIN( alpha[v], Edge[v][i].c - Edge[v][i].f );
queue[qe] = i; qe++; //顶点i入队列
}
else if( Edge[i][v].cINF Edge[i][v].f 0 ) //反向且有流量
{
flag[i] = 0; prev[i] = -v; //给顶点i标号(已标号未检查)
alpha[i] = MIN( alpha[v], Edge[i][v].f );
queue[qe] = i; qe++; //顶点i入队列
}
}
}
flag[v] = 1; //顶点v已标号已检查
}//end of while( qsqe flag[n-1]==-1 )
//当汇点没有获得标号,或者汇点的调整量为0,应该退出while循环
if( flag[n-1]==-1 || alpha[n-1]==0 ) break;
//当汇点有标号时,应该进行调整了
int k1 = n-1, k2 = abs( prev[k1] );
int a = alpha[n-1]; //可改进量
while( 1 )
{
if( Edge[k2][k1].fINF ) //正向
Edge[k2][k1].f = Edge[k2][k1].f + a;
else Edge[k1][k2].f = Edge[k1][k2].f - a; //反向
if( k2==0 ) break; //调整一直到源点v0
k1 = k2; k2 = abs( prev[k2] );
}//end of while( 1 )
}//end of while( 1 )
//输出各条弧及其流量,以及求得的最大流量
int maxFlow = 0;
for( i=0; i
文档评论(0)