//P4779【模板】单源最短路径(标准版)
//适用于不含负权值路径的图
#include <iostream>
#include <cstdio>
#include <algorithm>
#include <queue>
using namespace std;
#define MAXN 100005
#define MAXM 500005
#define INF 2147483647
int N,M,S;
int edge_num=0;
int head[MAXN]={0};
bool used[MAXN]={false};
int dis[MAXN]={0};
struct eg
{
int next;
int to;
int dis;
}edge[MAXM];//链式向前星储存
void scanff()
{
int a,b,c;
cin>>N>>M>>S;
for(int i=1;i<=M;i++)
{
cin>>a>>b>>c;
edge[++edge_num].next=head[a];
edge[edge_num].to=b;
edge[edge_num].dis=c;
head[a]=edge_num;
}
for(int i=1;i<=N;i++)
dis[i]=INF;
dis[S]=0;
}
struct Node
{
int dis;//点到原点距离
int pos;//点的编号
bool operator <( const Node &x )const
{
return x.dis < dis;
}
};//重载小于号。注意不要忘记头文件cstdio!
priority_queue<Node> pq;//堆优化
void dijkstra()
{
pq.push((Node){0,S});//将原点推入堆中
while(!pq.empty())
{
Node temp=pq.top();
//每次取到原点距离最短到点,作为距离确定点并pop掉
pq.pop();
if(used[temp.pos])//重复推入堆中,已求得最短路径,不用再计算
continue;
used[temp.pos]=true;//这个点已从堆中被推出(确定了最短距离)
//遍历所有以temp.pos为起点到边
for(int i=head[temp.pos];i;i=edge[i].next)
{
int t=edge[i].to;
if(dis[t]>dis[temp.pos]+edge[i].dis)
{
//更新最短距离
dis[t]=dis[temp.pos]+edge[i].dis;
if(!used[t])
{
pq.push((Node){dis[t],t});
}
}
}
}
for(int i=1;i<=N;i++)
cout<<dis[i]<<" ";
}
int main()
{
freopen("in.in","r",stdin);
freopen("out.out","w",stdout);
scanff();
dijkstra();
return 0;
}
单源最短路径:dijikstra
最新推荐文章于 2024-10-09 20:23:29 发布