JAVA实现Prim算法求村间修路最短路径问题

Prim算法求村子间修路最短路径问题:

  • 1、首先得有一个图的类,属性包括:图的节点个数、节点数据(A、B、C、D村)、节点间的关系(二维数组邻接矩阵)
  • 2、利用上面图的这个类,构建一个图(和链表的节点构建链表、数的结点构建数类似)
  • 3、显示这个图的邻接矩阵(村子间路的长度的关系)
  • 4、prim算法
  • 4.1、肯定需要定义一个visited[] 数组,用来表示以及访问过的节点,下标表示不同节点,值=0表示没访问过,值=1表示访问过了
  • 4.2、写个双重for循环来遍历邻接矩阵中的每一种可能。
    • 4.2.1 需要的是上面所有可能中:visited[i]==1&&visited[j]==0的情况,即一个顶点已经访问过,和这个顶点相连的没访问过的顶点 连成的边
    • 4.2.2 还要缩小范围到一个最小值:graph.weight[i][j] < minWeight(连成的边有多条,找最小值)
  • 4.3、双重循环结束后,找到的是一条最小的边,有 graph.verxs顶点,普利姆算法结束后,有 graph.verxs-1边,所以外面再加一个循环
  • 4.4、将当前这个结点(4.2找到的)标记为已经访问
  • 4.5、minWeight 重新设置为最大值 10000(遍历过程中一直被换成越来越小的,最小的就是找到的值)
package cn.edu.uestc.Prim;

import java.util.Arrays;


public class PrimAlgorithm {
    public static void main(String[] args) {
       MinTree minTree = new MinTree();
       char[] data = {'A','B','C','D','E','F','G'};
       int vertex = data.length;
       int[][] weight = new int[][]{
               {10000,5,7,10000,10000,10000,2},
               {5,10000,10000,9,10000,10000,3},
               {7,10000,10000,10000,8,10000,10000},
               {10000,9,10000,10000,10000,4,10000},
               {10000,10000,8,10000,10000,5,4},
               {10000,10000,10000,4,5,10000,6},
               {2,3,10000,10000,4,6,10000},
       };

       MGraph mGraph = new MGraph(vertex);
       //要什么给什么
       minTree.createGraph(mGraph,vertex,data,weight);//这个方法只是对mGraph初始化
       minTree.showGraph(mGraph);
       minTree.prim(mGraph,0);


    }

}
class MinTree{//最小生成数(各个村子的连接图)
    /**
     * 利用MGraph创建图
     */
    public void createGraph(MGraph mGraph, int vertex, char data[], int[][] weight){
        mGraph.vertex = vertex;
        mGraph.date = data;
        mGraph.weight = weight;
       /* int i, j;
        for(i = 0; i < verxs; i++) {//顶点
            graph.data[i] = data[i];
            for(j = 0; j < verxs; j++) {
                graph.weight[i][j] = weight[i][j];
            }
        }*/
    }

    /**
     * 显示图的邻接矩阵
     * @param mGraph
     */
    public void showGraph(MGraph mGraph){
        for (int[] data : mGraph.weight){
            System.out.println(Arrays.toString(data));
        }
    }

    /**
     * prim算法,得到最小生成数
     * @param v 表示从图的第几个顶点开始生成'A'->0 'B'->1...
     */
    public void prim(MGraph mGraph, int v){
        int visited[] = new int[mGraph.vertex];
        visited[v] = 1;//从这个开始,这个第一个标记为已经访问,后续从这个点开始找最近的路修路
        int minWeight = 10000;
        int[][] weight = mGraph.weight;
        int h1 = 0;//存放i、j(即村子对应矩阵下标是哪一个)
        int h2 = 0;

        for (int k = 1; k < mGraph.vertex; k++) { //根据prim算法,有vertex个顶点,最后就会有vertex-1条边



            for (int i = 0; i < mGraph.vertex; i++) {
                for (int j = 0; j < mGraph.vertex; j++) {
                    if (visited[i] == 1 && visited[j] == 0 && weight[i][j] < minWeight) {
                        h1 = i;
                        h2 = j;
                        minWeight = weight[i][j];
                    }
                }
            }
            //双重for循环结束后,完成的是一条最佳路径的寻找,下次寻找还得重新来。另外,这时候j也成为已经访问过的了
            minWeight = 10000;
            visited[h2] = 1;
            //每次二重for都生成了一条我们要的路
            System.out.println(mGraph.date[h1] + " 村与 " + mGraph.date[h2] + " 村完成修路,长度为: " + weight[h1][h2]);
        }


    }
}

class MGraph{
    int vertex;//英文单词 顶点的意思, 这里表示节点个数
    char[] date; // 节点的值:A村、B村、C村....
    int[][] weight; //存放边,就是邻接矩阵

    public MGraph(int vertex) {
        this.vertex = vertex;
        date = new char[vertex];
        weight = new int[vertex][vertex];
    }
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值