ICode9

精准搜索请尝试: 精确搜索
首页 > 编程语言> 文章详细

Prim算法(java)

2022-02-02 17:04:07  阅读:226  来源: 互联网

标签:Prim int graph 权值 maxValue 最小 算法 顶点 java


一、Prim算法介绍

  Prim(普利姆)算法是一种构造最小生成树的算法。Prim算法的时间复杂度为 O ( ∣ V ∣ 2 ) O(|V|^2) O(∣V∣2),不依赖于 E E E,因此它适用于求解边稠密的图的最小生成树。

二、Prim算法原理

  (1)初始时从图中任取一顶点加入最小生成树MinTree顶点集合中。
  (2)选择一个与当前MinTree中顶点集合距离最近的顶点,并将该顶点和相应的边加入MinTree中,每次操作后MinTree中的顶点数和边数都增1。
  (3)重复(2)步骤,直到所有顶点都加入到MinTree中,得到最小生成树。此时MinTree中有 n − 1 n-1 n−1条边。

三、Prim算法图解

在这里插入图片描述
  构造图(a)的最小生成树过程如下:
  (1)从顶点 V 1 V_{1} V1​开始,离 V 1 V_{1} V1​最近的三个顶点为 V 2 、 V 3 、 V 4 V_{2}、V_{3}、V_{4} V2​、V3​、V4​,选取权值最小的顶点 V 3 V_{3} V3​,加入顶点集合中,并将边< V 1 , V 3 V_{1},V_{3} V1​,V3​>加入最小生成树中。(如图b所示)
  (2)此时顶点集合为( V 1 , V 3 V_{1},V_{3} V1​,V3​),离顶点集合中最近的顶点为 V 2 、 V 4 、 V 5 、 V 6 V_{2}、V_{4}、V_{5}、V_{6} V2​、V4​、V5​、V6​,选取权值最小的顶点 V 6 V_{6} V6​,加入顶点集合中,并将边< V 3 , V 6 V_{3},V_{6} V3​,V6​>加入最小生成树中。(如图c所示)
  (3)此时顶点集合为( V 1 , V 3 , V 6 V_{1},V_{3},V_{6} V1​,V3​,V6​),离顶点集合中最近的顶点为 V 2 、 V 4 、 V 5 V_{2}、V_{4}、V_{5} V2​、V4​、V5​,选取权值最小的顶点 V 4 V_{4} V4​,加入顶点集合中,并将边< V 6 , V 4 V_{6},V_{4} V6​,V4​>加入最小生成树中。(如图d所示)
  (3)此时顶点集合为( V 1 , V 3 , V 6 、 V 4 V_{1},V_{3},V_{6}、V_{4} V1​,V3​,V6​、V4​),离顶点集合中最近的顶点为 V 2 、 V 5 V_{2}、V_{5} V2​、V5​,选取权值最小的顶点 V 2 V_{2} V2​,加入顶点集合中,并将边< V 3 , V 2 V_{3},V_{2} V3​,V2​>加入最小生成树中。(如图e所示)
  (4)此时顶点集合为( V 1 , V 3 , V 6 、 V 4 、 V 2 V_{1},V_{3},V_{6}、V_{4}、V_{2} V1​,V3​,V6​、V4​、V2​),离顶点集合中最近的顶点为 V 5 V_{5} V5​,选取权值最小的顶点 V 5 V_{5} V5​,加入顶点集合中,并将边< V 2 , V 5 V_{2},V_{5} V2​,V5​>加入最小生成树中。(如图f所示)
  (5)此时顶点集合为( V 1 , V 3 , V 6 、 V 4 , V 2 、 V 5 V_{1},V_{3},V_{6}、V_{4},V_{2}、V_{5} V1​,V3​,V6​、V4​,V2​、V5​),所有顶点已加入到集合中。最小生成树的边为< V 1 , V 3 V_{1},V_{3} V1​,V3​>、< V 3 , V 6 V_{3},V_{6} V3​,V6​>、< V 6 , V 4 V_{6},V_{4} V6​,V4​>、< V 3 , V 2 V_{3},V_{2} V3​,V2​>、< V 2 , V 5 V_{2},V_{5} V2​,V5​>。

四、Prim算法代码实现

package com.haiyang.algorithm.prim;

/**
 * @author haiYang
 * @create 2022-02-01 16:57
 */
public class PrimAlgorithm {
    public static void main(String[] args) {
        
        char[] data = new char[]{'A', 'B', 'C', 'D', 'E', 'F', 'G'};
        int vertexs = data.length;
        //maxValue表示两个顶点之前没有边
        int maxValue = Integer.MAX_VALUE;
        //邻接矩阵的关系使用二维数组表示,maxValue表示两个点不联通
        int[][] weight = new int[][]{
                {maxValue, 5, 7, maxValue, maxValue, maxValue, 2},
                {5, maxValue, maxValue, 9, maxValue, maxValue, 3},
                {7, maxValue, maxValue, maxValue, 8, maxValue, maxValue},
                {maxValue, 9, maxValue, maxValue, maxValue, 4, maxValue},
                {maxValue, maxValue, 8, maxValue, maxValue, 5, 4},
                {maxValue, maxValue, maxValue, 4, 5, maxValue, 6},
                {2, 3, maxValue, maxValue, 4, 6, maxValue}};
        Graph graph = new Graph(vertexs, data, weight);
        prim(graph, 0);


    }

    /**
     * @param graph 图
     * @param v     开始顶点
     */
    public static void prim(Graph graph, int v) {
        //标记已访问顶点
        int[] visited = new int[graph.vertexs];
        //将开始顶点标记已访问
        visited[v] = 1;
        //h1、h2标记最小的权值weight位置
        int h1 = -1;
        int h2 = -1;
        //记录最小权值
        int minWeight = Integer.MAX_VALUE;
        //除开始顶点,将其他graph.verrtexs-1个顶点进行选取
        for (int k = 1; k < graph.vertexs; k++) {

            //遍历图的所有情况,找到此轮的最小权值连接的顶点
            for (int i = 0; i < graph.vertexs; i++) {
                for (int j = 0; j < graph.vertexs; j++) {
                    //选取的顶点要求:i是已经选取的的顶点,j是为选取的顶点,找到满足情况的最小权值,记录位置
                    if (visited[i] == 1 && visited[j] == 0 && graph.weight[i][j] < minWeight) {
                        minWeight = graph.weight[i][j];
                        h1 = i;
                        h2 = j;
                    }
                }

            }
            //将此轮选取的最小权值连接的顶点信息输出
            System.out.println("边<" + graph.data[h1] + "," + graph.data[h2] + "> 权值=" + minWeight);
            //将此轮选取的顶点标记为已访问
            visited[h2] = 1;
            //重新初始化minWeight值
            minWeight = Integer.MAX_VALUE;

        }


    }
}

/**
 * 图类
 */
class Graph {
    int vertexs; //表示顶点个数
    char[] data;//存放顶点数据
    int[][] weight; //使用邻接矩阵存放边

    public Graph(int vertexs, char[] data, int[][] weight) {
        this.vertexs = vertexs;
        this.data = data;
        this.weight = weight;
    }
}

标签:Prim,int,graph,权值,maxValue,最小,算法,顶点,java
来源: https://blog.csdn.net/weixin_43698993/article/details/122770231

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有