目录

算法思想🐼 

算法步骤🐼 

DOC注释🐼 

代码实现(核心代码)🐼

1.创建寻找第一个邻接节点的方法🐻

代码分析:🐨

2.创建寻找后一个邻接节点的方法🐻

代码分析:🐨 

3.创建核心DFS(深度优先搜索)的方法🐻

代码分析:🐨

4.对DFS进行重载🐻

代码分析:🐨 

DeBug与图解🐼

结论:


算法思想🐼 

  • 从访问初始节点出发,访问初始节点可能有很多个邻接节点,深度优先算法的策略是首先访问第一个邻接节点,然后再以这个被访问的邻接节点作为访问初始节点,接着访问他的第一个邻接节点
  • 即:每次访问完当前节点首先访问当前节点的第一个邻接节点
  • 不难看出,访问策略往纵向发掘深入,而不是对一个节点的所有邻接节点进行访问
  • 显然,深度优先搜索算法是一个递归的过程

算法步骤🐼 

  1.  访问初始节点v,并将该节点标记为已读
  2.  查找初始节点的第一个邻接节点w
  3.  如果邻接节点w存在,则执行4,若不存在,则返回-1,从v的下一个未访问的节点继续
  4.  若w未被访问,对w进行深度优先搜索递归(即把w当作另一个v,然后再进行123)
  5.  若w被访问,查找节点v的w的下一个邻接节点,转到3

DOC注释🐼 

绘制深度学习模型逻辑图的网站_数据结构

请认真查阅Javadoc注释,否则无法看得懂下面的代码的目的 


代码实现(核心代码)🐼

1.创建寻找第一个邻接节点的方法🐻

public int getFirstVertex(int index) {
        for (int i = 0; i < vertexList.size(); i++) {
            if (edges[index][i] > 0) {
                return i;
            }
        }
        return -1;
    }

代码分析:🐨

  1. 通过邻接矩阵我们就可以得到各节点之间边的权值,根据权值我们就可以得到其邻接节点,故,我们需要用到邻接矩阵这个二维数组
  2. for循环的详解:
  1. i初始化为0的目的是:"找到第一个邻接节点"这句话得出,为了保证第一,所以要从下标为0的元素开始遍历
  2. i<vertexList.size()的目的是:在元素内遍历,防止空指针异常;即,将所有的元素遍历一遍
  3. 如果edges[index][i] > 0,说明有边,为当前下标元素的邻接节点,返回该节点下标
  1. 如果循环后没有返回任何数据,说明该节点没有任何邻接节点,直接返回-1

2.创建寻找后一个邻接节点的方法🐻

public int getVertexByLast(int v1,int v2) {
        for (int i = v2 + 1; i < vertexList.size() ; i++) {
            if (edges[v1][i] > 0) {
                return i;
            }
        }
        return -1;
    }

代码分析:🐨 

  1. 方法说明:该方法本质意思是找到当前节点的下一个邻接节点(如:JKL是他的邻接节点,第一次找到J,则调用该方法就会找到K)
  2. for循环的详解
  1. i = v2+1,其原因是"找到下一个邻接节点",如果将i赋值为v2,v2就是v1的一个邻接节点,直接返回,造成死循环,所以,找到他下一个邻接节点至少从他的下一个位置开始,切必须从该位置开始
  2.  i<vertexList.size()的目的是:在元素内遍历,防止空指针异常;即,将所有的元素遍历一遍
  1. 同理方法1后面的几句话

3.创建核心DFS(深度优先搜索)的方法🐻

该方法严格遵守算法步骤执行 

private void dfs(boolean[] isVisited,int v) {
        System.out.println(getItem(v));
        isVisited[v] = true;
        var w = getFirstVertex(v);
        while (w != -1) {
            if (!isVisited[w]) {
                dfs(isVisited, w);
            }
            w = getVertexByLast(v,w);
        }
        dfs();
    }

代码分析:🐨

  1. 先输出当前节点对应的数据
  2.  并将该节点标记成已读
  3.  获取当前节点的第一个邻接节点
  4.  若该邻接节点存在,则进入循环
  5.  若该邻接节点未被读取,则递归进入,继续进行DFS(深度优先)
  6.  否则找到下一个邻接节点,继续判断是否被读取
  7.  如果该邻接节点不存在,则寻找下一个未被读取的节点

4.对DFS进行重载🐻

@First("The DFS should be firstly invoked")
public void dfs() {
        for (int i = 0; i < vertexList.size(); i++) {
            if (!isVisited[i]) {
                dfs(isVisited,i);
            }
        }
}

代码分析:🐨 

  1. 该方法的目的是:寻找一个未被读取的节点,为了方便算法,我们默认从下标为0的节点开始
  2.  如果未被读取,则调用3方法,这个方法就实现了算法找不到邻接节点时所需要的操作

DeBug与图解🐼


绘制深度学习模型逻辑图的网站_java_02

以该"图"展开分析

绘制深度学习模型逻辑图的网站_java_03

对应的邻接矩阵(ABCDE下标对应01234)

  

绘制深度学习模型逻辑图的网站_数据结构_04

 

绘制深度学习模型逻辑图的网站_绘制深度学习模型逻辑图的网站_05

 

绘制深度学习模型逻辑图的网站_代码分析_06

 

绘制深度学习模型逻辑图的网站_java_07

 

绘制深度学习模型逻辑图的网站_java_08

 

绘制深度学习模型逻辑图的网站_算法_09

 

绘制深度学习模型逻辑图的网站_数据结构_10

绘制深度学习模型逻辑图的网站_数据结构_11

 

绘制深度学习模型逻辑图的网站_绘制深度学习模型逻辑图的网站_12

绘制深度学习模型逻辑图的网站_java_13

绘制深度学习模型逻辑图的网站_数据结构_14

 

绘制深度学习模型逻辑图的网站_java_15

 

绘制深度学习模型逻辑图的网站_代码分析_16

绘制深度学习模型逻辑图的网站_代码分析_17

 

绘制深度学习模型逻辑图的网站_算法_18

绘制深度学习模型逻辑图的网站_java_19

 同理得出"C"第一次找到的邻接节点是"A",第二次是"B",直到这一步 

绘制深度学习模型逻辑图的网站_java_20

 

绘制深度学习模型逻辑图的网站_算法_21

 

绘制深度学习模型逻辑图的网站_数据结构_22

 

绘制深度学习模型逻辑图的网站_数据结构_23

绘制深度学习模型逻辑图的网站_绘制深度学习模型逻辑图的网站_24

 debug结束,剩余的逻辑与以上的逻辑一致,相信友友们可以自行解决


结论:

         DFS算法比较抽象,不知道这种讲述方式大家能否可以接受,我来总结一下必须要掌握的几点:

        1.算法步骤如何进行

        2.算法思想如何理解(重点理解为什么是纵向深入)

        3.算法如何构建

下一站:图的广度优先算法