Heavy Transportation POJ - 1797 (最短路變形,最小邊最大化)

N個點,M條邊,每條邊有權值。求一條1號點到N號點的路徑,要求使得路徑中的邊權最小值最大。

Input
多組輸入,第一行給一個T。
每一組第一行給兩個數n和m。(1 <= n <= 1000)
接下來m行,每行三個數u,v,w代表路徑的兩個端點與邊權。
(1 <= u,v <= n , 0< w <= 1e6)
保證兩點間只有一條邊,該圖爲無向圖。

Output
第i組數據先輸出 “Scenario #i:”
然後輸出該路徑上的最小邊權,外加一個空行。
保證有解

Sample Input
1
3 3
1 2 3
1 3 4
2 3 5

Sample Output
Scenario #1:
4

思路:dist[i]表示從1到i的路徑中最大化的最小邊權。如果存在一條j->i的邊,那麼dist[i]=max(dist[i],min(dist[v],dis[i,j]))
要求最大化最小值,所以堆裏面的最小值不一定是該點最大化的最小值,只有最大值纔是該點確定的最大化最小值,所以必須開大頂堆纔可以。

#include<iostream>
#include<cstring>
#include<cmath>
#include<cstdio>
#include<queue> 
#include<vector>
#include<utility>
typedef long long ll;
#define pii pair<int,int> 
using namespace std;
const int N=200010;
int n,t;
int h[N],e[N],ne[N],w[N],cnt;
void add(int a,int b,int c)
{
	e[cnt]=b;
	w[cnt]=c;
	ne[cnt]=h[a];
	h[a]=cnt++;
}
int dist[N];

bool st[N];
void dij()
{
	for(int i=1;i<=n;i++) dist[i]=0,st[i]=false;
	dist[1]=0x3f3f3f3f;
	priority_queue<pii,vector<pii>,less<pii> > q;
	q.push(make_pair(dist[1],1)); 
	while(q.size())
	{
		int t=q.top().second;
		q.pop();
		if(st[t]) continue;
		for(int j=h[t];j!=-1;j=ne[j])
		{
			int v=e[j];
			if(dist[v]<min(dist[t],w[j]))
			{
				dist[v]=min(dist[t],w[j]);
				q.push(make_pair(dist[v],v));
			}
		}
		st[t]=1;
	}
	return ;
}
int idx,m;
int main()
{
	scanf("%d",&t);
	while(t--)
	{
		scanf("%d%d",&n,&m);
		cnt=0;
		for(int i=0;i<=n;i++) h[i]=-1;
		for(int i=1;i<=m;i++) 
		{
			int a,b,c;
			scanf("%d%d%d",&a,&b,&c);
			add(a,b,c);add(b,a,c);
		}
		dij();
		printf("Scenario #%d:\n%d\n\n",++idx,n==1?0:dist[n]);//注意輸出格式
	}
	return 0;
}

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章