图-java语言描述

1、图的一些基本概念

  • 图:每个节点都可以有零个或多个前驱,也可以有零个或多个后继,也就是说,元素之间的关系是任意的。也可以称为多对多。
  • 节点:组成图的重要部分
  • 边:两个节点的连接
  • 无向图:节点之间的连接没有方向
  • 有向图:节点之间的连接有方向
  • 带权图(网):权就是节点中的值
  • 路径:一个节点到另一个节点所经过的路程
  • 图的表示方法
    • 邻接矩阵(用二维数组表示):表示图形之中节点间相邻关系的矩阵
    • 邻接表(用数组+链表表示):数组之中存放了这个图中所有的节点,每一个数组又是一个链表的头节点,该链表表示这个节点与多少个节点有连接
  • 图的深度优先遍历:先遍历每一个节点的第一个邻接节点,也就是纵向的遍历
    • 步骤:
    • 1、访问初始节点 i,并将该节点标记为已访问
    • 2、查找节点 i的第一个邻接节点 j
    • 3、若 j存在:
      • 若 j未被访问,则对 j进行深度优先遍历,也就是把 j当作新的 i,递归
      • 若 j被访问,则对 i的的其他邻接节点继续重复上述步骤
    • 4、若 j不存在:则对 i的其他邻接节点继续重复上述步骤,若没有其他邻接节点,就结束该递归,回到上一层
    • 5、直至所有的节点都已判断完毕,结束
  • 图的广度优先遍历:先遍历一个节点的所有邻接节点,再去遍历其他节点,也就是横向的遍历,类似于一个分层搜索,需要先使用一个队列保持访问过的节点的顺序,以便于按照这个顺序访问这些节点的邻接节点。
    • 步骤:
    • 1、访问初始节点 i,并将该节点标记为已访问,该节点入队列
    • 2、当队列为非空的时候,继续执行,否则算法结束(注意:这里的算法结束是指对当前 i的算法)
    • 3、出队列,取得该队列的头部节点 j
    • 4、查找节点 j的第一个邻接节点 k
      • 1、若节点 k不存在,则回到 3
      • 2、若节点 k存在,则:
        • 1、若节点 k未被访问,则将 k标记为已访问,k入队列
        • 2、查找节点 j的继节点 k的下一个邻接节点 k,回到步骤 5

2、一些常用的方法

	//1、得到节点的数目
    public int getNumOfVertex() {
   
        return vertexList.size();
    }

    //2、得到边的数目
    public int getNumOfEdges() {
   
        return numOfEdges;
    }

    //3、得到第几个节点对应的数据
    public String getValueByIndex(int i) {
   
        return vertexList.get(i);
    }

    //4、返回v1、v2的权值
    public int getWeight(int v1, int v2) {
   
        return edges[v1][v2];
    }

    //5、显示图对应的矩阵
    public void showGraph() {
   
        for (int[] link : edges) {
   
            System.out.println(Arrays.toString(link));
        }
    }

    /**
     * 6、得到当前节点的邻接节点的下标
     *
     * @param i 传入的节点的下标
     * @return 该节点的第一个邻接节点的下标,没有的话就返回 -1
     */
    public int getFirstNeighbor(int i) {
   
        for (int j = 0; j < vertexList.size(); j++) {
   
            if (edges[i][j] > 0) {
   
                return j;
            }
        }
        return -1;
    }

    /**
     * 7、根据前一个邻接节点的下标获取到下一个邻接节点的下标
     *
     * @param v1 前一个邻接节点
     * @param v2 要查找邻接节点的节点
     * @return 返回当前节点的邻接节点
     */
    public int getNextNeighbor(int v1, int v2) {
   
        for (int j = v2 + 1; j < vertexList.size(); j++) {
   
            if (edges[v1][j] > 0) {
   
                return j;
            }
        }
        return -1;
    }

3、深度优先遍历

	/**
     * 深度优先遍历
     *
     * @param isVisited 该图所有的节点是否被访问的数组
     * @param i         从第 i个节点开始
     */
    private void dfs(boolean[] isVisited, int i) {
   
        //首先输出第一个被访问的节点
        System.out.print(getValueByIndex(i) + "->");
        //将节点设置为已访问
        isVisited[i] = true;
        //查找第 i个节点的邻接节点
        int j = getFirstNeighbor(i);

        //判断该节点是否有邻接节点
        while (j != 
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值