数据结构与算法|最小生成树算法(普里姆算法、克鲁斯卡尔算法)

最小生成树算法

C语言代码部分来自小甲鱼的《数据结构与算法》


最小生成树:一个有 n 个结点的连通图的生成树是原图的 极小连通子图,且包含原图中的所有 n 个结点,并且有保持图连通的最少的边。

​ 最小生成树可以用kruskal(克鲁斯卡尔)算法或prim(普里姆)算法求出,它们考虑问题的出发点是:为使生成树上边的权值之和达到最小,则应使生成树中每一条边的权值尽可能的小。

​ 普里姆算法是以某个顶点为起点,逐步找到每个顶点上最小权值的边来构建最小生成树。克鲁斯卡尔算法则换一种思路,从边出发,因为权值是在边上,所以直接去找最小权值的边来构建生成树。

区别:当边较多顶点较少时,用普里姆算法比较快;当边较少顶点较多时,用克鲁斯卡尔算法比较有优势

一、普里姆(Prim)算法

在这里插入图片描述

1.C语言代码

#include "math.h"
#include "stdio.h"

#define MAXVEX 50


typedef struct MGraph
{
   
    char vex[MAXVEX];       // 顶点集合
    int numVertexes;           // 顶点数
    int numedg;           // 边数
    int arc[MAXVEX][MAXVEX]; // 邻接矩阵
}MGraph;
//=============================================//
//=============================================//


//Prim算法生成最小生成树
void MiniSpanTree_Prim(MGraph G)
{
   
    int min,i,j,k;
    int adjvex[MAXVEX]; //保存相关顶点下标
    int lowcost[MAXVEX]; //保存相关顶点间边的权值

    lowcost[0]=0;       //V0作为最小生成树的根开始遍历,权值为0(当走到哪里时,显示所有联结的边)
    adjvex[0]=0;        //V0第一个加入(这是路径)

    //初始化操作
    for(i=1;i<G.numVertexes;i++)
    {
   
        lowcost[i]=G.arc[0][i];  //将邻接矩阵第0行所有权值先加入数组
        adjvex[i]=0;             //初始化全部先为V0的下标
    }


    //真正构造最小生成树的过程
    for(i=1;i<G.numVertexes;i++)
    {
   
        min=INFINITY;  //初始化最小权值为不可能数值inf
        j=1;
        k=0;

        //遍历全部顶点
        while (j<G.numVertexes)
        {
   
            //找出lowcaost数组已存储的最小权值(查找最小可走边)
            if(lowcost[j]!=0 && lowcost[j]<min)
            {
   
                min=lowcost[j];
                k=j;        //将发现的最小权值的下标存入k,以待使用。
            }
            j++;
        }

        //打印当前顶点边权值最小的边
        printf("(%d,%d)",adjvex[k],k);  //adjvex是路径
        lowcost[k]=0;  //将当前顶点的权值设置为0,表示此顶点已经完成任务,进行下一个顶点的遍历

        //邻接矩阵k行逐个遍历全部顶点
        for(j=1;j<G.numVertexes;j++)
        {
   
            if(lowcost!=0 && G.arc[k][j]<lowcost
  • 1
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值