【算法学习】搜索算法之深度优先搜索

news/2024/7/20 22:16:48 标签: 算法, 学习, 深度优先

深度优先搜索

DFS

1.算法介绍

深度优先搜索(DFS)算法是一种用于遍历或搜索树或图的算法。它的基本思想是尽可能深地搜索图的分支,直到到达叶节点或无法再深入为止,然后回溯到前一个节点,继续探索其他分支。这种搜索策略可以确保图中的每个节点都被访问到,除非它是一个环。
深度优先搜索的实现通常使用递归或栈来实现。对于树或图的遍历,可以从根节点或任意节点开始,然后沿着某个分支深入搜索,直到达到叶节点或无法再深入为止。在这个过程中,需要记录已经访问过的节点,以避免重复访问。当一条路径搜索完成后,需要回溯到上一个节点,继续搜索其他分支。

2.算法原理

深度优先搜索(DFS)算法的原理主要基于图的遍历。给定一个图(可以是有向图或无向图),DFS从某个起始节点出发,尽可能深地搜索图的分支,直到达到叶节点或无法再深入为止。然后,它回溯到上一个节点,继续搜索其他未遍历的分支。这个过程反复进行,直到图中所有可达的节点都被访问过。
DFS使用栈(stack)这种数据结构来辅助实现。在搜索过程中,将当前访问的节点以及从起始节点到该节点的路径上的所有节点都放入栈中。当搜索到叶节点或无法再深入时,从栈中弹出当前节点,并回溯到上一个节点,继续搜索。
DFS的核心思想包括两个方面:
1.回溯(backtracking):当搜索到叶节点或无法再深入时,需要回溯到上一个节点,继续搜索其他未遍历的分支。这种走不通就退回再走的技术称为回溯法。满足回溯条件的某个状态的点称为“回溯点”。
2.剪枝(pruning):在搜索过程中,通过某些条件判断,提前终止对当前分支的搜索,以减少不必要的搜索。这种减小搜索树规模、尽早排除搜索树中不必要的分支的手段称为剪枝。
DFS的时间复杂度在最坏情况下为O(n!),其中n为图中节点的数量。这是因为对于每个节点,都可能有n种选择(即选择下一个要访问的节点),从而导致搜索树的规模达到n的阶乘。然而,在实际应用中,DFS通常能在较小的搜索空间内找到解,因此其平均时间复杂度往往低于最坏情况。

3.算法实现

下面是一个使用C语言实现的深度优先搜索(DFS)算法示例。在这个示例中,我们使用邻接矩阵来表示图,并使用递归来实现DFS。

#include <stdio.h>
#include <stdbool.h>

#define MAX_VERTICES 100

// 函数原型声明
void dfs(int graph[MAX_VERTICES][MAX_VERTICES], bool visited[], int v);

int main() {
    // 示例图的邻接矩阵表示
    // 1 表示存在边,0 表示不存在边
    int graph[MAX_VERTICES][MAX_VERTICES] = {
        {0, 1, 1, 0, 0, 0, 0, 0, 0, 0},
        {1, 0, 0, 1, 1, 0, 0, 0, 0, 0},
        {1, 0, 0, 0, 0, 1, 0, 0, 0, 0},
        {0, 1, 0, 0, 0, 1,

http://www.niftyadmin.cn/n/5385549.html

相关文章

软考笔记--信息系统开发方法(下)

信息系统是一个极其复杂的人机交互系统&#xff0c;它不仅包含计算机技术&#xff0c;通信技术和网络规划以及其他的工程技术&#xff0c;而且&#xff0c;它还是一个复杂的管理系统&#xff0c;需要管理理论和方法的支持&#xff0c;因此&#xff0c;与其他工程项目相比&#…

深入理解java虚拟机---自动内存管理

2.2 运行时数据区域 Java虚拟机在执行Java程序的过程中会把它所管理的内存划分为若干个不同的数据区域。这些区域有各自的用途&#xff0c;以及创建和销毁的时间&#xff0c;有的区域随着虚拟机进程的启动而一直存在&#xff0c;有些区域则是依赖用户线程的启动和结束而建立和销…

文件上传漏洞--Upload-labs--Pass17--条件竞争

一、条件竞争原理&#xff08;结合代码审计&#xff09; 1、首先进行代码审计&#xff0c;查看源代码。 我们可知&#xff0c;将文件上传至服务器后&#xff0c;不会被立即删除&#xff0c;而是做短暂的停留&#xff0c;中间会有一小部分时间差&#xff0c;这部分时间差是代码…

HTML单击图片独立放大

代码&#xff1a; <style>.modal {display: none;position: fixed;z-index: 9999;top: 0;left: 0;width: 100%;height: 100%;background-color: rgba(0, 0, 0, 0.8);}.modal-image {display: block;max-width: 90%;max-height: 90%;margin: auto;margin-top: 5%;} </…

抽象方法与设计模式

抽象方法与设计模式 设计模式的六大原则工厂模式单例模式建造者模式过滤器模式装饰器模式享元模式责任链模式模板模式 真正的屎山不是初级程序员写的巨量胶水代码&#xff0c;而是没学明白抽象的程序员写的大量设计模式耦合形成的。你甚至不理解为什么当初的创作者需要使用到这…

代码随想录刷题第38天

今天正式进入动态规划。首先了解了动态规划的基本问题与动规五步曲&#xff1a;1.明确DP数组与下标含义&#xff1b;2.给出递推公式&#xff1b;3.初始化DP数组&#xff1b;4.明确遍历顺序&#xff1b;5.打印DP数组。 第一题是斐波那契数https://leetcode.cn/problems/fibonac…

数据结构之时空复杂度

一、前言 1&#xff09;什么是数据结构 数据结构(Data Structure)是计算机存储、组织数据的方式&#xff0c;指相互之间存在一种或多种特定关系的数据元素的 集合。 2&#xff09;什么是算法 算法(Algorithm):就是定义良好的计算过程&#xff0c;他取一个或一组的值为输入&am…

计算机二级C语言的注意事项及相应真题-6-程序修改

目录 51.从整数10到55之间&#xff0c;选出能被3整除、且有一位上的数是5的那些数&#xff0c;并把这些数放在b所指的数组中&#xff0c;这些数的个数作为函数值返回52.先将s所指字符串中的字符按逆序存放到t所指字符串中&#xff0c;然后把s所指串中的字符按正序连接到t所指串…