C#,迭代深化搜索(IDS)或迭代深化深度优先搜索(IDDFS)算法的源代码

摘要:本文介绍适合于大数据规模情况下的,新型的迭代深化深度优先搜索(IDDFS)算法的原理、实例及实现的C#源代码。

引言

常用的树(或图)遍历算法是两种: 广度优先搜索算法(BFS)深度优先搜索算法(DFS)。然而在遇到巨大高度和宽度的树(或图)时,BFS 和 DFS 都不是非常有效。因为:

(1)DFS首先遍历通过根的一个相邻节点,然后遍历下一个相邻节点。这种方法的问题是,如果有一个节点靠近根,但不在DFS探索的前几个子树中,那么DFS到达该节点的时间很晚。此外,DFS可能无法找到到节点的最短路径(根据边的数量)。而,BFS 一级一级的走,但是需要更多的空间。

(2)DFS 需要的空间是 O(d),其中 d 是树的深度,但是 BFS 需要的空间是 O(n),其中 n 是树中的节点数(为什么?请注意,树的最后一级可以有大约 n/2 个节点,第二个最后一级可以有 n/4 个节点,在 BFS,我们需要让每一级都一个接一个地排队)。

IDDFS (迭代深化深度优先搜索,Iterative Deepening Depth-First Search,也简称为IDS)则是结合了深度优先搜索的空间效率和广度优先搜索的快速搜索(对于更接近根的节点)。

这里发布IDDFS 主要的原理性的代码,更全面的程序可在此基础上改进与增强。

一、IDDFS简介

迭代深化深度优先搜索(IDDFS)是一种算法,与BFS和DFS一样,它也是非信息搜索策略的重要组成部分。我们可以将IDDFS定义为BFS和DFS搜索技术的混合算法。在IDDF中,我们发现BFS和DFS存在一定的局限性,因此我们对这两种程序进行了混合,以消除它们各自的缺点。我们先进行有限深度搜索,直到固定的“有限深度”。然后,我们通过迭代过程不断增加深度限制,除非我们找到了目标节点或遍历了整个树(以较早的为准)。

二、IDDFS的工作原理

在非信息搜索策略中,BFS和DFS在最佳时间和空间搜索元素方面并不理想。这些算法只能保证在指数时间和空间中找到路径。因此,我们找到了一种方法,我们可以使用DFS的空间能力和BFS方法的最优解方法的融合,在那里我们开发了一种新的方法,称为迭代深化,使用这两种方法。这里的主要思想在于利用边界实体的重新计算,而不是囤积它们。每次重新计算都由DFS组成,因此占用的空间更少。现在让我们考虑在迭代加深搜索中使用BFS。

考虑将广度优先搜索转化为迭代加深搜索。

我们可以通过留出一个DFS来做到这一点,它将搜索到一个极限。它首先搜索到预定义的深度到深度的限制,然后生成路由长度1。

这是通过以DFS方式创建长度为1的路由来实现的。接下来,它为深度限制2、3及以上的路线让路。

它甚至可以在循环开始时删除所有之前的计算并进行迭代。因此,在某种程度上,如果树中存在任何问题,最终会找到解决方案,因为枚举是按顺序进行的。

伪代码:

IDDFS(T):
for d = 0 to infinity:
    if (DLS(T, d)):
        return 1
    else
        return 0

为了实现迭代深化搜索,我们必须标记以下各项之间的差异:

(1)当达到深度极限界限时发生破裂。

(2)未达到深度界限的故障。

而在这种情况下,我们通过每次增加深度限制来多次尝试搜索方法,在第二种情况下,即使我们继续搜索多次,因为不存在解决方案,这意味着浪费时间。因此,我们得出结论,在第一种情况下,失败被发现是非自然的失败,在第二种情况下,失败是自然的。

三、IDDFS实例

咱们看看一个实例:

在给定的树中,起始节点是A,深度初始化为0。目标节点是R,我们必须找到到达它的深度和路径。图中的深度为4。在这个例子中,我们考虑树作为有限树,而我们也可以考虑同样的过程的无限树。我们知道在IDDFS算法中,我们首先进行DFS,直到指定的深度,然后增加每个循环的深度。这个特殊步骤是DLS或深度限制搜索的一部分。因此,下面的遍历显示了IDDFS搜索。

四、IDDF的优点和缺点

以下是优点和缺点。

1、优势

(1)IDDFS让我们有希望找到树中存在的解决方案。

(2)当在较低的深度(例如n)找到解时,该算法被证明是有效且及时的。

(3)IDDFS的最大优势是在博弈树搜索中发现,IDDFS搜索操作试图改进搜索节点的深度定义、启发式和得分,从而提高搜索算法的效率。

(4)IDDFS算法的另一个主要优点是响应速度快。早期结果是该算法的一个优点。在单独的迭代完成后,进行了多次改进。

(5)虽然在这里做了更多的工作,但IDDF的性能优于单独的BFS和DFS。

(6)空间和时间复杂性表示为:O(d),这里d被定义为目标深度。

(7)让我们考虑IDDFS的运行时间。假设b>l,其中b是分支因子,l是深度极限。然后,我们在边界k下搜索目标节点。在深度k上,我们说可能有只生成一次的节点。类似地,深度限制k-1处的节点是k-2深度的两倍和三倍。因此,在深度l处生成的节点是k倍。

2、缺点

(1)到达目标节点所需的时间是指数级的。

(2)IDDF的主要问题是在每个深度进行的时间和浪费的计算。

(3)情况并不像我们想象的那么糟糕,尤其是当分支因子被发现很高时。

(4)当BFS失败时,IDDF可能会失败。当我们要从IDDF中找到多个答案时,它会一次返回成功节点及其路径,即使在多次迭代后需要再次找到它。停止深度限制不会进一步增加。

五、结论

迭代深化深度优先搜索是BFS和DFS的混合算法。IDDF可能不会直接用于计算机科学的许多应用中,但该策略通过迭代增加深度限制来搜索无限空间的数据。这非常有用,在人工智能和新兴的数据科学行业中也有应用。

六、IDDFS的C#源代码

下面给出IDDFS的核心算法C#源代码。C#最优雅!

using System;
using System.IO;
using System.Text;
using System.Collections;
using System.Collections.Generic;

namespace Legalsoft.Algorithm.Graph
{
    public class NodeInfo
    {
        /// <summary>
        /// 序号
        /// </summary>
        public int Id { get; set; } = 0;
        /// <summary>
        /// 数据
        /// </summary>
        public string Value { get; set; } = "";
        /// <summary>
        /// 访问标识
        /// </summary>
        public bool Visited { get; set; } = false;
        /// <summary>
        /// 默认构造方法
        /// </summary>
        public NodeInfo()
        {
        }
        /// <summary>
        /// 构造函数
        /// </summary>
        /// <param name="id"></param>
        /// <param name="value"></param>
        public NodeInfo(int id, string value)
        {
            Id = id;
            Value = value;
        }
    }

    /// <summary>
    /// 边信息
    /// </summary>
    public class EdgeInfo
    {
        /// <summary>
        /// 起点Id
        /// </summary>
        public int From { get; set; } = -1;
        /// <summary>
        /// 终点Id
        /// </summary>
        public int To { get; set; } = -1;
        /// <summary>
        /// 默认构造方法
        /// </summary>
        public EdgeInfo()
        {
        }
        /// <summary>
        /// 构造方法
        /// </summary>
        /// <param name="from"></param>
        /// <param name="to"></param>
        public EdgeInfo(int from, int to)
        {
            From = from;
            To = to;
        }
    }
    /// <summary>
    /// 图信息
    /// </summary>
    public class IDDFS_Graph
    {
        /// <summary>
        /// 节点信息
        /// </summary>
        public List<NodeInfo> Nodes { get; set; } = new List<NodeInfo>();
        /// <summary>
        /// 图的边(连线)集合
        /// </summary>
        public List<EdgeInfo> Edges { get; set; } = new List<EdgeInfo>();

        /// <summary>
        /// 默认构造方法
        /// </summary>
        public IDDFS_Graph()
        {
        }

        /// <summary>
        /// 添加“边信息”用于构建“图”数据
        /// </summary>
        /// <param name="from"></param>
        /// <param name="to"></param>
        public void AddEdge(int idFrom, string valueFrom, int idTo, string valueTo)
        {
            if (!Nodes.Exists(t => t.Id == idFrom))
            {
                Nodes.Add(new NodeInfo(idFrom, valueFrom));
            }
            if (!Nodes.Exists(t => t.Id == idTo))
            {
                Nodes.Add(new NodeInfo(idTo, valueTo));
            }
            Edges.Add(new EdgeInfo(idFrom, idTo));
        }

        /// <summary>
        /// 从 src 开始的有限深度搜索
        /// </summary>
        /// <param name="src"></param>
        /// <param name="target"></param>
        /// <param name="limit"></param>
        /// <returns></returns>
        private bool Depth_Limited_Search(int src, int target, int limit)
        {
            if (src == target)
            {
                return true;
            }

            if (limit <= 0)
            {
                return false;
            }

            int i = Edges[src].From;
            while (i != Edges[src].To)
            {
                if (Depth_Limited_Search(i, target, limit - 1) == true)
                {
                    return true;
                }
                i++;
            }

            return false;
        }

        /// <summary>
        /// 迭代深化深度优先搜索
        /// </summary>
        /// <param name="src">起点</param>
        /// <param name="target">目标</param>
        /// <param name="max_depth">最大深度差</param>
        /// <returns></returns>
        public bool IDDFS(int src, int target, int max_depth)
        {
            // 深度控制
            for (int i = 0; i <= max_depth; i++)
            {
                if (Depth_Limited_Search(src, target, i) == true)
                {
                    return true;
                }
            }

            return false;
        }
    }
}

改进的IDDFS在AI领域有很不错的表现。

值得继续研究与改进。

---------------------------------------------
POWER BY TRUFFER.CN

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/303121.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

C#编程-实现文件输入和输出操作

实现文件输入和输出操作 所有程序接受用户的输入、处理输入并且产生输出。所以,所有的编程语言都支持输入和输出操作。例如,您需要为教师开发程序以接受学生的结果信息。您的程序应该将信息保存在硬盘的Result.xls文件中。您可以在程序中使用文件输入和输出操作以接受来自教…

外汇网站主要业务逻辑梳理

上图为工行ICBC的外汇保证金交易界面。 当需要买入帐户欧元&#xff08;欧元人民币&#xff09;时&#xff0c;买入100欧元&#xff0c;因为没有杠杆&#xff0c;虽然欧元中间价是782.34&#xff0c;但实际需要支付783.14元人民币的保证金&#xff0c;这个兑换不是真实的外汇兑…

全网独家:基于openeuler-20.03-lts底包构建opengauss数据库V5.0.1LTS的单机容器

近期想测试一下opengauss数据库,官网上单机容器部署只有x86-64平台CentOS 7.6和ARM64平台 openEuler20.03 LTS两种底包方案。本文系全网独家在x86平台上基于openeuler-20.03-lts底包构建opengauss数据库V5.0.1LTS的单机容器。 opengauss官网上单机容器部署只有x86-64平台Cent…

计算机毕业设计 基于javaweb的学生交流培养管理平台/系统的设计与实现 Java实战项目 附源码+文档+视频讲解

博主介绍&#xff1a;✌从事软件开发10年之余&#xff0c;专注于Java技术领域、Python人工智能及数据挖掘、小程序项目开发和Android项目开发等。CSDN、掘金、华为云、InfoQ、阿里云等平台优质作者✌ &#x1f345;文末获取源码联系&#x1f345; &#x1f447;&#x1f3fb; 精…

910b上跑Chatglm3-6b进行流式输出【pytorch框架】

文章目录 准备阶段避坑阶段添加代码结果展示 准备阶段 配套软件包Ascend-cann-toolkit和Ascend-cann-nnae适配昇腾的Pytorch适配昇腾的Torchvision Adapter下载ChatGLM3代码下载chatglm3-6b模型&#xff0c;或在modelscope里下载 避坑阶段 每个人的服务器都不一样&#xff0…

Unity3d 实现直播功能(无需sdk接入)

Unity3d 实现直播功能 需要插件 :VideoCapture 插件地址(免费的就行) 原理:客户端通过 VideoCapture 插件实现推流nodejs视频流转服务进行转发,播放器实现rtmp拉流 废话不多说,直接上 CaptureSource我选择的是屏幕录制,也可以是其他源 CaptureType选择LIVE–直播形式 LiveSt…

IDEA[Debug]简单说明

目录 &#x1f95e;1.打断点 &#x1f32d;2.第一组按钮 &#x1f9c2;3.第二组按钮 &#x1f953;4.参数查看 1.打断点 1.在需要断点处打上断点&#xff0c;然后点击debug运行 2.执行debug&#xff0c;直接执行到断点处 2.第一组按钮 共有8按钮&#xff0c;从左往右依…

【系统高级-环境变量】path配置一整行,而不是列表

这是列表编辑方便。但是不知道为什么变成一行&#xff0c;非常的令人抓狂&#xff0c;经过研究发现&#xff0c;第一个环境变量必须为C:\Windows\system32 开头才可以 文章如下 修改环境变量中的一行变成列表形式_环境变量编辑不是列表-CSDN博客

回归预测 | Matlab实现RIME-HKELM霜冰算法优化混合核极限学习机多变量回归预测

回归预测 | Matlab实现RIME-HKELM霜冰算法优化混合核极限学习机多变量回归预测 目录 回归预测 | Matlab实现RIME-HKELM霜冰算法优化混合核极限学习机多变量回归预测效果一览基本介绍程序设计参考资料 效果一览 基本介绍 1.Matlab实现RIME-HKELM霜冰算法优化混合核极限学习机多变…

苍穹外卖Day01——总结1

总结1 1. 软件开发整体介绍1.1 软件开发流程1.2 角色分工1.3 软件环境 2. 苍穹外卖项目介绍2.1 项目介绍2.2 技术选项 3. Swagger4. 补充内容&#xff08;待解决...&#xff09; 1. 软件开发整体介绍 1.1 软件开发流程 1.2 角色分工 从角色分工里面就可以查看自己以后从事哪一…

芯片命名大全:完整的器件型号包括主体型号、前缀、后缀等!

不少公司的采购会发现&#xff0c;拿到工程师提供的BOM中的器件去采购物料时&#xff0c;经常供应商还会问得更仔细&#xff0c;否则就不知道供给你哪种物料&#xff0c;严重时&#xff0c;采购回来的物料用不了。为什么会有这种情况呢&#xff1f;问题就在于&#xff0c;很多经…

数据结构—图(下)

文章目录 12.图(下)(4).生成树和最小生成树#1.什么是生成树和最小生成树&#xff1f;i.生成树ii.最小生成树 #2.Prim算法i.算法思想ii.看看例子iii.代码实现 #3.Kruskal算法i.算法思想ii.看看例子iii.代码实现 #4.次小生成树 (5).最短路径问题#1.加权有向图的最短路径问题#2.单…

盘点三款服务器运维工具

随着世界变得更加数字化&#xff0c;如何便捷高效地管理服务器变得越来越重要&#xff0c;能有一款简易实用且现代化服务器管理工具就显得尤为关键。今天就选取了三款服务器运维工具进行对比分析&#xff0c;评测每款产品的优缺点。 产品清单 宝塔面板 简介&#xff1a;国内老…

工作流自动化:它是什么,常见示例以及如何实现

由于您的组织旨在留住顶尖人才和高价值客户&#xff0c;因此您需要不断为这两个团队提供一流的体验。 就客户而言&#xff0c;它可以实时解决他们的问题和疑虑&#xff0c;并以深思熟虑、可操作的洞察力主动与他们联系&#xff1b;而且&#xff0c;对于员工来说&#xff0c;它可…

推荐一款强大的AI开源项目!有了它,将你的数据库秒变AI数据库!

前言 在当今数字化的世界中&#xff0c;数据库系统扮演着至关重要的角色。而原生系统的功能我们也大都知晓&#xff0c;无非是一些增删改查、数据优化的使用。但有一些开源工具项目可以帮助我们对数据库降本增效。 在本文中&#xff0c;小编将介绍一个名为SuperDuperDB的开源…

构建多种样式的弹窗(案例)

介绍 本篇Codelab将介绍如何使用弹窗功能&#xff0c;实现四种类型弹窗。分别是&#xff1a;警告弹窗、自定义弹窗、日期滑动选择器弹窗、文本滑动选择器弹窗。需要完成以下功能&#xff1a; 点击左上角返回按钮展示警告弹窗。点击出生日期展示日期滑动选择器弹窗。点击性别展示…

树莓派4B使用ncnn部署yolov5-Lite,推理耗时 247ms 包含前后处理

一. 引言 最近在玩树莓派&#xff0c;想在树莓派上不是一个目标检测算法&#xff0c;大致看了一下&#xff0c;目前开源的大家都在使用yolov5-Lite&#xff0c;使用ncnn去推理加速&#xff0c;于是自己也尝试部署&#xff0c;在此记录一下&#xff0c;个人踩的坑。 二. 版本选…

后端 API 接口文档 Swagger 使用

Swagger 是什么 swagger是一款可以根据 restful 风格生成的接口开发文档&#xff0c;并且支持做测试的一款中间软件。 例如当我们在开发前后端分离项目时&#xff0c;当后端开发完一个功能想要测试时&#xff0c;若此时还没有相应的前端页面发起请求&#xff0c;可以通过 swag…

java回溯算法、最短路径算法、最小生成树算法

回溯算法 回溯算法实际上一个类似枚举的搜索尝试过程&#xff0c;主要是在搜索尝试过程中寻找问题的解&#xff0c;当发现已不满足求解条件时&#xff0c;就“回溯”返回&#xff0c;尝试别的路径。 最短路径算法 从某顶点出发&#xff0c;沿图的边到达另一顶点所经过的路径中…

【QML COOK】- 002-添加一个图片

1. 编辑main.qml import QtQuickWindow {width: 800height: 800visible: truetitle: qsTr("Hello World")Image {anchors.fill: parentsource: "qrc:/Resources/Images/arrow.png"} }将Window的width和height都改成800&#xff0c;因为我们要添加的图片大…