关于图的构造,图的遍历

5 篇文章 0 订阅
1 篇文章 0 订阅

本代码是用Java实现了关于图的一些方法,其中包含了图的深度优先遍历,广度优先遍历,图中各顶点的出度,入度计算。具体代码实现如下所示:

import java.util.LinkedList;

public class Graph {
    private int verTexSize;//顶点数量
    private int[] verTex;//顶点数组
    private int[][] matrix;//邻接矩阵
    private static final int MAX_WEIGHT=1000;
    private boolean[] isVisited;//顶点是否被访问数组

    /**
     * 构造方法
     * @param verTexSize
     */
    public Graph(int verTexSize){
        this.verTexSize=verTexSize;
        matrix=new int[verTexSize][verTexSize];
        verTex=new int[verTexSize];

        for (int i=0;i<verTexSize;i++){
            verTex[i]=i;
        }
        isVisited=new boolean[verTexSize];
    }

    public int getVerTexSize() {
        return verTexSize;
    }

    public void setVerTexSize(int verTexSize) {
        this.verTexSize = verTexSize;
    }

    /**
     * 获取给定节点的出度
     * @param index
     * @return
     */
    public int getOutDegree(int index){
        int degree=0;
        for (int i=0;i<matrix[index].length;i++){
            int weight=matrix[index][i];
            if (weight!=0&&weight!=MAX_WEIGHT){
                degree++;
            }
        }
        return degree;
    }

    /**
     * 获取给定节点的入度
     * @param index
     * @return
     */
    public int getInDegree(int index){
        int degree=0;
        for (int j=0;j<matrix.length;j++){
            int weight=matrix[j][index];
            if (weight!=0&&weight!=MAX_WEIGHT){
                degree++;
            }
        }
        return degree;
    }

    /**
     * 获取给定两个顶点的权重
     * @param v1
     * @param v2
     * @return
     */
    public int getWeight(int v1,int v2){
        int weight=matrix[v1][v2];
        if (weight==0||weight==MAX_WEIGHT){
            return -1;
        }
        return weight;
    }

    /**
     * 获取第一个邻节点
     * @param index
     * @return
     */
    public int getFirstNeibor(int index){
        for (int i=0;i<verTexSize;i++){
            if (matrix[index][i]>0&&matrix[index][i]<MAX_WEIGHT){
                return i;
            }
        }
        return -1;
    }

    /**
     * 获取其他邻接点
     * @param v
     * @param index
     * @return
     */
    public int getNextNeibor(int v,int index){
        for (int j=index+1;j<verTexSize;j++){
            if (matrix[v][j]>0&&matrix[v][j]<MAX_WEIGHT){
                return j;
            }
        }
        return -1;
    }

    /**
     * 深度优先遍历
     * @param i
     */
    private void depthFirstSearch(int i){
        isVisited[i]=true;
        int w=getFirstNeibor(i);
        while(w!=-1){
            if (!isVisited[w]){
                System.out.println("遍历到了:" + w + "顶点");
                depthFirstSearch(w);
            }
            w = getNextNeibor(i,w);
        }
    }

    /**
     * 深度优先遍历对外暴露的方法
     */
    public void depthFirstSearch(){
        isVisited= new boolean[verTexSize];
        for (int i=0;i<verTexSize;i++){
            if (!isVisited[i]){
                System.out.println("遍历到了:" + i + "顶点");
                depthFirstSearch(i);
            }
        }
        isVisited= new boolean[verTexSize];
    }

    /**
     * 广度优先遍历,对外暴露的方法
     */
    public void broadFirstSearch(){
        isVisited=new boolean[verTexSize];
        for (int i=0;i<verTexSize;i++){
            if (!isVisited[i]){
                broadFirstSearch(i);
            }
        }
    }

    /**
     * 广度优先遍历
     * @param i
     */
    private void broadFirstSearch(int i) {
        //u表示接收出队的元素,w表示u的邻接点
        int u,w;
        //创建队列,因为队列实现了链表的接口
        LinkedList<Integer> queue=new LinkedList<>();
        System.out.println("遍历到了" + i + "顶点");
        isVisited[i]=true;
        queue.add(i);
        while(!queue.isEmpty()){
            u=queue.removeFirst();
            w=getFirstNeibor(u);
            //判断u是否含有邻接点
            while (w!=-1){
                if (!isVisited[w]){
                    System.out.println("遍历到了" + w + "顶点");
                    isVisited[w]=true;
                    queue.add(w);
                }
                //获取u的非第一个邻接点
                w=getNextNeibor(u,w);
            }

        }
    }

}

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值