【模板题】【图】Floyd 多源最短路+求最小环 RQNOJ 389 心灵的抚慰

本文介绍了解决RQNOJ389问题的思路与实现,该问题要求寻找不含特定顶点k的最短环路。通过调整Floyd算法的遍历顺序,并在更新最短路径前检查环路的存在,最终得出解决方案。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

RQNOJ 389 心灵的抚慰

 

思路:问题在于求一个i->j不含k的路径。此时假设k为环中最大的序号点,则d[i][j]不会包含点k,k+1,k+2...。若真正的最小环包含点k,k+1,k+1...,则当前求得的不是全局最小环。

注意:
1、遍历顺序k、i、j(先遍历经过点)
2、求ans一定要放在更新d[i][j]之前,因为在之前最短路更新过程中,k没有参与更新,所以dis[i][j]所表示的路径中不会出现k,如果成立,则一定是一个环。
3、遍历起终点。求最小环i=1~k-1,j=i+1~k-1(因为不能经过点k)。朴素Floyd都是1~n

#include<iostream>
#include<string.h>
#define INF 1<<27
using namespace std;
int n,m;
int g[251][251];
int d[251][251];
int ans=INF;
void Floyd()
{
	int i,j,k;
	for (k=1;k<=n;k++)
	{
		for (i=1;i<k;i++)//不能经过k
			for (j=i+1;j<k;j++)//不能经过k
				ans=min(ans,d[i][j]+g[j][k]+g[k][i]);//保证至少经过3个点
		for (i=1;i<=n;i++)
			for (j=1;j<=n;j++)
				d[i][j]=min(d[i][j],d[i][k]+d[k][j]);
	}
}
int main()
{
	int i,a,b,t,j;
	cin>>n>>m;
	for (i=1;i<=n;i++)
		for (j=1;j<=n;j++)
		{
			d[i][j]=INF;g[i][j]=INF;
		}
	for (i=0;i<m;i++)
	{
		cin>>a>>b>>t;
		g[a][b]=min(t,g[a][b]);
		g[b][a]=min(t,g[b][a]);
		d[a][b]=g[a][b];
		d[b][a]=g[b][a];
	}
	Floyd();
	if (ans==INF)
		cout<<"He will never come back."<<endl;
	else cout<<ans<<endl;
	return 0;
}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值