最小生成树之Prim算法

Prim算法介绍:
假设N = (V, {E})是连通网,TE是N上最小生成树中边的集合。算法U={u0}(u0ЄV),TE={}开始,重复执行下述操作:在所有uЄU,vЄV-U的边(u,v)ЄE中找一条代价最小的边(u0,v0)并入集合TE,同时v0并入U,直至U=V为止。此时TE中必有n-1条边,则T=(V,{TE})为N的最小生成树。
Prim算法构造最小生成树的过程如下:
在这里插入图片描述
代码如下:

import java.util.Arrays;
import java.util.Scanner;

public class prim {
    public static void main(String args[ ]){
        Scanner scanner = new Scanner(System.in);
        int n =  scanner.nextInt();
        int m = scanner.nextInt();
        int[][] cost = new int[n+1][n+1];
        for(int i = 1; i<n+1; i++){
            Arrays.fill(cost[i], Integer.MAX_VALUE);
        }
        for(int i = 0; i<m; i++){
            int x = scanner.nextInt();
            int y = scanner.nextInt();
            int p = scanner.nextInt();
            cost[x][y] = cost[y][x] = p;
        }
        prim(cost, n, Integer.MAX_VALUE);
    }

    public static void prim(int[][] cost, int n, int maxi){
        int lowcost[] = new int[n+1];
        int closest[] = new int[n+1];

        for(int i = 2; i<n+1; i++){
            lowcost[i] = cost[1][i];
            closest[i] = 1;
        }
        int min, m;
        //寻找邻近最小路径
        for(int i = 2; i<n+1; i++){
            min = maxi;
            m = 1;
            for(int j = 2; j<n+1; j++){
                if(lowcost[j] < min && lowcost[j] != 0){
                    m = j;
                    min = lowcost[j];
                }
            }
            //输出生成树的边
            System.out.println("closest[" + m + "]=" + closest[m]);
            lowcost[m] = 0;
            closest[m] = 0;
            //调整代价
            for(int j = 2; j<n+1; j++){
                if(cost[m][j] < lowcost[j] && cost[m][j] != 0){
                    lowcost[j] = cost[m][j];
                    closest[j] = m;
                }
            }
        }
    }
}

Prim算法时间复杂度为O(n2),与网中的边数无关,因此适用于求边稠密的网的最小生成树。

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值