读《人工智能》第二章笔记+讨论题

53 阅读10分钟

第二章 盲目搜索

2.0 简介:智能系统中的搜索

2.1 状态空间图

状态空间图:对应于给定问题的所有可能状态的结构。 状态空间图(state-space graph)是对问题的一种表示方法。问题的解通常需要在 这个结构中进行搜索(无论它是树还是图),搜索始于起始节点,止于终点或目标状态

2.2 生成-测试范式

生成-测试范式:先给出可能的解,再检查每个可能的解,看是否有候选解能够构成问题的解。这种方式被称为生成-测试范式。(本节用 n 皇后问题来解释这种方式)

n皇后问题: 如果这个生成器给出了每个可能的解,那么该生成器就是完备的(complete)。如果某个给出的解被拒绝,那么这个解就不会再次被给出(事实上,即使是成功的解也只能给出一次)。换句话说,一个好的生成器应该是非冗余的。 如果生成器有一些信息,允许其对给出的解做出一些限制,那么这个生成器就是知情的(informed)。

生成-测试范式的过程: {While 没有找到解,但仍有候选方案 [生成可能的解 测试其是否满足所有的问题约束条件] End While} IF 找到某个解,则宣布成功,并输出此解 Else 宣布没有找到解

2.2.1 回溯法

如果问题的约束条件得到满足,那么搜索将进行到下一步。如果任何选择都得不到可行的部分解,那么搜索将回溯到前一步,撤销前一步的选择,继续下一个可能的选择结果。

如果第 i 个皇后摆放在任意棋格中都违反约束条件,那么必须返回到第 i—1 步。

  1. 完全枚举法
  2. 回溯法:针对某个问题,给出解的过程会被分成多个步骤

2.2.2 贪心算法

基本定义:

顾名思义,贪心算法采用贪心的策略,保证每次操作都是局部最优的,从而是最后得到的结果是全局最优。(有时候会失效) Dijkstra 最短路径算法blog.csdn.net/qq_44977889… 这里的流程图解释得很清楚

2.2.3 旅行商问题

给定 n 个顶点的加权图(即每条边上带有开销值),求从某个顶点 Vi出发经过加权图中的所有顶点(每个顶点只经过一次),然后返回到Vi的最短路径。 在这一问题中,贪心算法不一定能找到最佳路径

分支定界(branch and bound)算法是广度优先搜索的一种变体。在这种搜索算法中,节点按照开销不减少的原则进行探索。分支定界算法又称为统一代价搜索(uniform cost search)

2.3 盲目搜索算法

盲目搜索算法是不使用问题域知识的不知情搜索算法。这些算法假定不知道状态空间的任何信息。 主要的盲目搜索算法如下:

  • 深度优先搜索(DFS)
  • 广度优先搜索(BFS)
  • 迭代加深的深度优先搜索(DFS-ID)

这些算法都具有如下两个性质:

  1. 不使用启发式估计
  2. 它们的目标是找出给定问题的某个解。

2.3.1 深度优先搜索(DFS)

定义:顾名思义,就是试图尽可能快地深入树中进行搜索。每当搜索方法可以做出选择时,就选择最左(或最右)分支(通常选择最左分支)。

避免重复状态是许多高效搜索算法的基本特征

2.3.2 广度优先搜索(BFS)

定义:从树的顶部到树的底部,按照从左到右(或从右到左)的方式,可以逐层访问节点。必须首先访问第 i层的所有节点,然后才能访问第 i +1 层的节点。

2.4 盲目搜索算法的实现和比较

本节将提供实现这两种搜索算法的伪代码,并讨论它们在问题求 解中的相对优势以及它们的时空需求。

2.4.1 深度优先搜索的实现

先前介绍的搜索算法的共同做法——维护两张表:

  • 开放表:包含了树中所有待探索(或扩展)的节点
  • 封闭表:包含了所有已探索和不再考虑的节点

DFS伪代码如下:

Begin

Open ?[Start state]

//开放表被维护为堆栈,即,插入的最后一个项目是删除的第一个项目的列表。这通常被称为LIFO(后进 先出)列表。

Closed ?[ ]

//封闭表:包含了所有已探索和不再考虑的节点;

//并且封闭表最初是空的

While 开放表不是空的

  Begin

    删除开放表的第一个项目,称之为X

    如果X等于目标,则返回"成功"

    Else

    生成X的直系后代

    将X放在封闭表中。

    如果已经遇到X的子节点,则丢弃

//循环检查

Else 将尚未遇到的子节点放在开放表上

//end else

//end While

返回 “未找到目标”

某个节点一旦被访问,就被移到开放表的头部,以确保下一次能生成其子节点

2.4.2 广度优先搜索的实现

广度优先搜索则探索靠近根的所有节点,然后才深入探索搜索树。

广度优先搜索用队列来表示开放表。队列是一种**先进先出(FIFO)**的数据结构。一旦节点被扩展,其子节点就会移动到开放表的尾部。因此,只有在其父节点所在层中的每个其他节点都被访问之后,才会访问这些子节点。

BFS伪代码如下:

Begin Open?[Start state]

//The open list is maintained as a queue,i.e.,a list in which the first item inserted is the first item deleted.

//This is often referred to as a FIFO list.

Closed?[]

//The closed list contains nodes that have already been inspected;it is initially empty.

Whle Open not empty Begin

    Remove first item trom Open,call it X.

    If X equals goal then return Success

    Else

    Generate immediate descendants of X

    Put X on Closed List..

    If children of X already encounteredthen discard.//loop check

    Else place children not yet encountered on Open

    //end else

    //end while

    Return,Goal not found

End Algoritthm breadth first search

2.4.3 问题求解性能的衡量指标

  • 完备性:当问题存在解时,如果搜索算法可以保证找到一个解,就说这个算法是完备的
  • 最优性:如果搜索算法能提供所有解中那个开销最低的解,则认为这个算法是最优的
  • 时间复杂度:关注的是找到解需要花费的时间。这里可以根据搜索期间生成(或扩展)的节点数量来衡量
  • 空间复杂度:搜索算法的空间复杂度(space complexity)关注的是内存开销。我们必须确定存储到内存中的最大节点数目。AI 中的复杂度是用如下 3 个参数表示的:
  1. 分支因子b
  2. 最浅目标节点的深度d
  3. 状态空间中所有路径的最大长度m

2.4.4 DFS 和 BFS 的比较

当:

  • 树很深
  • 分支因子不太大,且解出现在树中的位置相对较深 时。DFS比BFS好。 当:
  • 搜索树的分支因子不太大
  • 解出现在树中的位置在合理的深度,且所有路径都不是特别深。 时。BFS比DFS好。

2.4.5 DFS-ID算法

对 BFS 而言,最尖锐的批评来自其指数级的空间复杂度。即使问题的规模不太大,BFS 也很快就变得不可行。结合 DFS 的中等存储空间需求,去除寻找长路径的倾向,可以得到迭代加深的 DFS,即 DFS-ID(DFS With Iterative Deepening)。

在最坏的情况下,所有的盲目搜索算法,包括 DFS、BFS 和 DFS-ID,都会表现出指数级的时间复杂度。DFS-ID 每次只需要在内存中存储一条路径,因此它的空间复杂度为 O(b*d),这与 DFS 相同

当分支因子有限时,与 BFS 一样,DFS-ID 是完备的。当路径开销是节点深度的非递减函数时,DFS-ID 是最优的。

讨论题

  1. 搜索为什么是 AI 系统的重要组成部分?

AI在问题解决、决策制定、学习还是优化方面上,都要接触大量数据,这些方面都离不开可以从数据海中寻找到有用的数据的搜索方法。

  1. 状态空间图是什么?

对应于给定问题的所有可能状态的结构。

  1. 描述生成-测试范式。

生成-测试范式就是先给出可能的解,再检查每个可能的解,看是否有候选解能够构成问题的解的方法。

  1. 生成器有什么属性?

  1. 回溯法如何对完全枚举法进行改进? 回溯法在搜索过程中,一旦发现当前选择无法满足问题的约束条件,就会立即停止当前路径的搜索,回溯到上一步进行新的尝试。这种操作避免了对无效解的完全枚举,大大提高了搜索效率。

  2. 用一两句话描述贪心算法。 顾名思义,贪心算法采用贪心的策略,保证每次操作都是局部最优的,从而使最后得到的结果是全局最优。

  3. 陈述旅行商问题。 给定 n 个顶点的加权图(即每条边上带有开销值),求从某个顶点 Vi出发经过加权图中的所有顶点(每个顶点只经过一次),然后返回到Vi的最短路径。

  4. 简述 3 种盲目搜索算法。

  • 深度优先搜索(DFS)
  • 广度优先搜索(BFS)
  • 迭代加深的深度优先搜索(DFS-ID)
  1. 在何种意义上,盲目搜索算法是盲目的?

盲目搜索算法不使用问题域知识的不知情搜索算法。这些算法假定不知道状态空间的任何信息,因此,在搜索的机械性上,盲目搜索算法是盲目的。

  1. 按照完备性、最优性和时空复杂性,比较本章描述的 3 种盲目搜索算法。
  • 完备性:如果搜索空间是有限的,三种盲目搜索算法都是完备的。
  • 最优性:DFS不保证开销最低地找到最优解,除非它搜索了所有的解;BFS可以保证找到的是最优解,因为它总是先搜索最浅的节点;DFS-ID可以保证找到的是最优解,因为它有深度限制
  • 时间复杂度:DFS、BFS的时间复杂度为O(b^d),在最坏的情况下,它们需要遍历整个搜索树。DFS-ID的时间复杂度为O(b^d),因为它实质上是在不同深度限制下重复进行DFS。
  • 空间复杂度:DFS的空间复杂性为O(bd),因为它只需要存储单个路径从根节点到当前节点,以及每个节点的未探索的子节点。BFS的空间复杂性为O(b^d),因为所有的节点都需要存储在内存中,以便按照宽度进行搜索。DFS-ID的空间复杂性为O(bd),因为它每次只进行有深度限制的DFS。
  1. 在什么情况下,DFS 比 BFS 好?
  • 树很深
  • 分支因子不太大,且解出现在树中的位置相对较深
  1. 在什么情况下,BFS 比 DFS 好?
  • 搜索树的分支因子不太大
  • 解出现在树中的位置在合理的深度,且所有路径都不是特别深。
  1. 在什么意义上,可以说 DFS-ID 是 BFS 和 DFS 的折中?

完备性和最优性、时间效率和空间效率上。