2021-06-22 邻接表Dijkstra算法可以输出最短路径和值

这里使用了结构体,一个存储最短路径,一个存前一个结点。这样就可以根据最后一个结点往前找,找出整个路径。

#include<stdio.h>
#include<string.h> 
#include<stdlib.h>
#define max 900000000 //表示两点之间无法连接 

typedef struct{ 
    int d;//到达某点的最短路径距离 
    int pre;//该最短路径是经过哪个点传过来的,用于存储路径 
}path; 

int main(){
    int n,m,a,b,v,i,j,min,k;
	char node[] = {"0ABCDEFGHIJKLMN"};//存储所有结点,加0是为了结点下标从1开始 
	char start1,last1;//初位置点 
	printf("请输入初末位置点:(空格隔开)\n");
	scanf("%c %c",&start1,&last1);
	int start2,last2;//初末位置点序号,一共点 
	//找出初末点对应的下标,和一共的点数 
	for(int i = 1;node[i]!='\0';i++)
	{
		if(node[i]==start1)
			start2 = i;
		if(node[i]==last1)
				last2 = i;
		n = i;//总点数 
	}
	
    int e[n+1][n+1],vis[n+1];//e[i][j]表示i到j的边的权值,vis[i]表示此点是否被遍历 
    path to[n+1];//记录当前到某个点的最短路径 
    memset(vis,0,sizeof(vis));
    for(i=0;i<=n;i++){ 
        for(j=0;j<=n;j++){ 
            e[i][j]=max; 
      }
        to[i].d=max;    
    }

    //存入图 
	e[1][2]=1,e[1][3]=1,e[1][4]=3;
    e[2][7]=2;
    e[3][5]=1;
    e[4][13]=3;
    e[5][6]=1;
    e[6][9]=2;
    e[7][10]=5;
    e[9][12]=3;
    e[10][12]=2;
	e[11][12]=2,e[11][14]=6;
	e[13][14]=5;
	//变成无向图 
	for(int i = 1;i<=n;i++)
	{
		for(int j = 1;j<=n;j++)
		{
			if(e[i][j] != max)
			e[j][i] = e[i][j];
		}
	}
	
	//准备初始结点 
    for(i=1;i<=n;i++)
	{
        to[i].d=e[start2][i]; //初始化源点到i点边权值,之后过程中会发生变化 
        if(e[start2][i]!=max)
		{
          to[i].pre=start2;  
        } 
    }
    vis[start2]=1;
    
    for(i=1;i<=n-1;i++)
	{//共循环n-1次,每循环一次,确定一条最短路,再次循环时这条路就不用考虑了,去寻找下一条最短路 
        min=max;
        for(j=1;j<=n;j++)
		{//寻找下一条当前最短路 
           if(to[j].d<min && vis[j]==0)
		   {
             min=to[j].d;
             k=j;
           }    
        }
        vis[k]=1;//找到了,到k点的路是当前最短路,标记它,根据它寻找下一条最短路 
        for(j=1;j<=n;j++)
		{
            if(e[k][j]<max)
            {
            	if(to[j].d>to[k].d+e[k][j]&&vis[j]==0)
				{//经过此k点到达j点的路径是否小于其他到达j点的路径 
                to[j].d=to[k].d+e[k][j];
                to[j].pre=k;//改变j点是谁传来的,现在到j点的最短路径是经过k点的,由j点传来  
                }
			}
        }
    }  
    
	if(to[last2].d != max)//判断是否能到达该点 
	{
		char sort[14]; 
		int count = 0;
		printf("%c到%c最短距离为%d \n",node[start2],node[last2],to[last2].d);
		j = last2;
		sort[count] = node[j];
		do{
            j=to[j].pre;
            count++;
            sort[count] = node[j];//存储路径是逆序,需要正序输出 
        }while(j!=start2);
        printf("最短路径为");
        while(count>=1)//正序输出 
        {
        	printf("%c->",sort[count]);
        	count--;
		}
		printf("%c",sort[0]);
	}
	
	else
	printf("无法到达该点!"); 
	
    return 0;
} 
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值