POJ-3268 Silver Cow Party (shortest path)

Topic link: Click View

Topic: Give n n points, m single paths and a point x. Let the distance from x to I and from I to x be D1 and d2, respectively, and find the maximum value of d1+d2 (1<=i<=n).

Topic analysis: The distance from point x to point i, d1, only needs to find the shortest path to point x once. The question is how to deal with the distance from point I to point x? It's not always possible to find the shortest path n times.

Let's judge one by one. It's bound to run out of time. Here's a clever way to think it out. It's basically no problem to use adjacency matrix to store edge information.

When d1 is solved, the matrix is transposed, and then the shortest path starting at x point is obtained once. The result is the shortest path from each point to X point.

Because when the matrix is transposed, the direction of each one-way edge is reversed, the shortest path for x-point is obtained at this time, and the shortest path for each point is obtained before processing.

It's the same. We all want the shortest path from point i to point x.

Note: In this question, I store d1 in an ans array, and then find the distance d after a spfa is equivalent to d2.

Code:

#include<iostream>
#include<cstdio> 
#include<string>
#include<cstring>
#include<algorithm>
#include<stack>
#include<queue>
#include<map>
#include<sstream>
#include<cmath>
using namespace std;

typedef long long LL;

const int inf=0x3f3f3f3f;

const int N=1e3+100;

int n,m,x;

int maze[N][N];

int d[N];

int ans[N];

bool vis[N];

void spfa(int x)
{
	memset(vis,false,sizeof(vis));
	memset(d,inf,sizeof(d));	
	vis[x]=true;
	d[x]=0;
	queue<int>q;
	q.push(x);
	while(!q.empty())
	{
		int tem=q.front();
		q.pop();
		vis[tem]=false;
		for(int i=1;i<=n;i++)
		{
			if(d[i]>d[tem]+maze[tem][i])
			{
				d[i]=d[tem]+maze[tem][i];
				if(!vis[i])
				{
					vis[i]=true;
					q.push(i);
				}
			}
		}
	}
}

int main()
{
//	freopen("input.txt","r",stdin);
	while(scanf("%d%d%d",&n,&m,&x)!=EOF)
	{
		for(int i=1;i<=n;i++)
			for(int j=1;j<=n;j++)
			{
				maze[i][j]=i==j?0:inf;
			}
		for(int i=1;i<=m;i++)
		{
			int a,b,c;
			scanf("%d%d%d",&a,&b,&c);
			maze[a][b]=c;
		}
		spfa(x);
		for(int i=1;i<=n;i++)
			ans[i]=d[i];
		for(int i=1;i<=n;i++)
			for(int j=1;j<i;j++)
				swap(maze[i][j],maze[j][i]);
		spfa(x);
		int mmax=0;
		for(int i=1;i<=n;i++)
		{
			if(ans[i]!=inf&&d[i]!=inf)
				mmax=max(mmax,ans[i]+d[i]);
		}
		cout<<mmax<<endl;
	}
	
	
	
	
	
	
	
	
	
	return 0;
} 

 

Posted by seikan on Tue, 30 Jul 2019 14:23:36 -0700