`
人生难得糊涂
  • 浏览: 114614 次
社区版块
存档分类
最新评论

POJ1789-SPFA

 
阅读更多

此题要注意松弛条件

 

#include<iostream>
#include<queue>
using namespace std;
#define MAXSIZE 1000
typedef struct node{
	int u;
	int v;
	double w;
	double c;
}node;
node p[MAXSIZE];
int head[MAXSIZE];
int next[MAXSIZE];
int n,m,s;
double dis[MAXSIZE];
double v;//v 为初始拥有的货币数量
int e;
queue<int>que;
int vis[MAXSIZE];
int cnum[MAXSIZE];

int spfa(int s)
{
	int i,j;
	while(!que.empty())
		que.pop();
	memset(vis,0,sizeof(vis));
	memset(cnum,0,sizeof(cnum));
	memset(dis,0,sizeof(dis));//初始时每个节点都没有钱
	vis[s]=1;
	cnum[s]++;
	dis[s]=v;
	que.push(s);
	while(!que.empty())//当队列非空
	{
		int te=que.front();
		que.pop();
		vis[te]=0;
		for(i=head[te];i!=-1;i=next[i])//取出te相连的所有点
		{
			//if 利益增加了 则松弛(对应于 路径变短)
			//(现在拥有的货币-手续费)*比率 等于可以换得的货币
			double tt=(dis[te]-p[i].c)*p[i].w;//dis[te] 表示te这个点拥有的资产
			if(dis[p[i].v]<tt)
			{
				dis[p[i].v]=tt;
				if(!vis[p[i].v])
				{
					vis[p[i].v]=1;
					cnum[p[i].v]++;
					que.push(p[i].v);
					if(cnum[p[i].v]>n)
					{
						return 1;
					}
				}
			}
		}
	}
	
	return 0;
}


void addnode(int u,int v,double w,double c)
{
	p[e].u=u;
	p[e].v=v;
	p[e].w=w;
	p[e].c=c;
	next[e]=head[u];
	head[u]=e++;
}
int main()
{
	//freopen("in.txt","r",stdin);
	//while(scanf("%d%d%d%lf",&n,&m,&s,&v)!=EOF)
	{
		scanf("%d%d%d%lf",&n,&m,&s,&v);
		e=0;
		memset(head,-1,sizeof(head));
		memset(next,-1,sizeof(next));
		while(m--)
		{	
			int a,b;
			double r1,c1,r2,c2;
			scanf("%d%d%lf%lf%lf%lf",&a,&b,&r1,&c1,&r2,&c2);
			addnode(a,b,r1,c1);
			addnode(b,a,r2,c2);
		}
		//spfa
		if(spfa(s))
			printf("YES\n");
		else
			printf("NO\n");

	}
}

 

分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics