Python 算法高级篇:启发式搜索与 A *算法

news2024/11/14 17:25:21

Python 算法高级篇:启发式搜索与 A *算法

  • 引言
  • 1. 什么是启发式搜索?
    • 1.1 启发式函数的特性
    • 1.2 启发式搜索算法
  • 2. A *算法的原理
    • 2.1 A *算法的伪代码
    • 2.2 A *算法的优点
  • 3. Python 中的 A *算法实现
  • 4. 总结

引言

启发式搜索是一种常用于解决路径规划和优化问题的算法,而 A *算法是其中的一种经典方法。本篇博客将深入探讨启发式搜索的原理,介绍 A *算法的工作方式,以及如何在 Python 中实现它。每一行代码都将有详细的注释,以帮助你理解算法的实现。

😃😄 ❤️ ❤️ ❤️

1. 什么是启发式搜索?

启发式搜索是一种问题解决方法,旨在在大规模搜索空间中寻找最优解或接近最优解的解。它使用一个启发式函数(也称为估价函数)来评估每个搜索节点,以确定哪些节点最有可能包含最优解。启发式函数提供了一种估计从当前节点到目标节点的代价或距离的方式,通常称为启发式值。

1.1 启发式函数的特性

一个良好的启发式函数应该满足以下特性:

  • 一致性( Consistency ): 启发式函数的估计值不应该高估实际代价。也就是说,如果启发式函数估计从节点 A 到节点 B 的代价为 h ( A ),而从节点 B 到节点 C 的代价为 d ( B , C ),那么 h ( A )不应该大于 d ( B , C ) + h ( C )。

  • 启发式值为 0 : 启发式函数应该在目标节点上返回 0 。这表示已经达到了最优解。

1.2 启发式搜索算法

在启发式搜索中,有两个核心概念:

  • 开放列表( Open List ): 包含待扩展的节点。节点根据启发式函数的值排列,最有希望的节点在前面。

  • 闭合列表( Closed List ): 包含已经扩展的节点。这些节点不会再次考虑。

启发式搜索通常包括以下步骤:

  • 1 . 将初始节点放入开放列表。
  • 2 . 重复执行以下步骤,直到达到目标节点或开放列表为空:
    • a . 从开放列表中选择具有最小启发式值的节点。
    • b . 如果选择的节点是目标节点,则算法结束。
    • c . 否则,将该节点从开放列表移到闭合列表,并扩展它的邻居节点。
  • 3 . 如果开放列表为空且未找到目标节点,则问题无解。

2. A *算法的原理

A *算法是一种启发式搜索算法,常用于路径规划和图搜索问题。它使用两个估价函数来指导搜索过程:

  • g ( n ): 从起始节点到节点 n 的实际代价。
  • h ( n ): 从节点 n 到目标节点的估计代价,由启发式函数提供。

A *算法的评估函数为 f ( n ) = g ( n ) + h ( n )。它尝试从开放列表中选择 f 值最小的节点进行扩展,期望能够找到最优解。

2.1 A *算法的伪代码

以下是 A *算法的伪代码:

function A*(start, goal)
    open_list = {start}  # 初始化开放列表,包含起始节点
    closed_list = {}     # 初始化闭合列表

    while open_list is not empty
        current = node in open_list with the lowest f
        if current is goal
            return reconstruct_path(goal)
        
        move current from open_list to closed_list

        for each neighbor of current
            if neighbor is in closed_list
                continue
            if neighbor is not in open_list
                add neighbor to open_list
            tentative_g = g(current) + distance(current, neighbor)
            if tentative_g >= g(neighbor)
                continue

            # This path is the best so far. Record it!
            g(neighbor) = tentative_g
            h(neighbor) = heuristic(neighbor, goal)
            f(neighbor) = g(neighbor) + h(neighbor)
            parent(neighbor) = current

    # Open list is empty but goal was never reached
    return "No path found"

2.2 A *算法的优点

A *算法具有以下优点:

  • 完备性:如果解存在, A *算法将找到最优解。
  • 最优性:当启发式函数满足一致性条件时, A *算法保证找到最优解。
  • 可配置性:可以根据不同问题和启发式函数来配置 A *算法。

3. Python 中的 A *算法实现

让我们来看一个在 Python 中实现 A *算法的示例,用于解决迷宫问题。

import heapq

def astar(grid, start, end):
    open_list = []
    heapq.heappush(open_list, (0, start))
    came_from = {}
    g_score = {cell: float('inf') for row in grid for cell in row}
    g_score[start] = 0
    f_score = {cell: float('inf') for row in grid for cell in row}
    f_score[start] = heuristic(start, end)

    while open_list:
        current_f, current = heapq.heappop(open_list)

        if current == end:
            return reconstruct_path(came_from, current)

        for neighbor in get_neighbors(current, grid):
            tentative_g = g_score[current] + 1
            if tentative_g < g_score[neighbor]:
                came_from[neighbor] = current
                g_score[neighbor] = tentative_g
                f_score[neighbor] = g_score[neighbor] + heuristic(neighbor, end)
                heapq.heappush(open_list, (f_score[neighbor], neighbor))

    return None  # No path found

# Helper functions for the A* algorithm
def heuristic(a, b):
    return abs(a[0] - b[0]) + abs(a[1] - b[1])

def get_neighbors(cell, grid):
    neighbors = []
    row, col = cell
    if row > 0 and not grid[row - 1][col]:
        neighbors.append((row - 1, col))
    if row < len(grid) - 1 and not grid[row + 1][col]:
        neighbors.append((row + 1, col))
    if col > 0 and not grid[row][col - 1]:
        neighbors.append((row, col - 1))
    if col < len(grid[0]) - 1 and not grid[row][col + 1]:
        neighbors.append((row, col + 1))
    return neighbors

def reconstruct_path(came_from, current):
    path = [current]
    while current in came_from:
        current = came_from[current]
        path.append(current)
    path.reverse()
    return path

# 示例:解决迷宫问题
grid = [
    [0, 0, 0, 0, 0],
    [0, 1, 1, 1, 0],
    [0, 1, 0, 0, 0],
    [0, 1, 1, 1, 0],
    [0, 0, 0, 0, 0]
]

start = (0, 0)
end = (4, 4)
path = astar(grid, start, end)
print("Path:", path)

这个示例演示了如何使用 A *算法解决迷宫问题,寻找从起点到终点的最短路径。

4. 总结

启发式搜索和 A *算法是解决路径规划和优化问题的有力工具。本博客中,我们了解了启发式搜索的原理,讨论了 A *算法的工作方式,并提供了 Python 中的实现示例。启发式搜索广泛应用于许多领域,包括人工智能、游戏开发和机器人路径规划。希望这篇博客有助于你理解和应用这些强大的算法。

[ 专栏推荐 ]
😃 Python 算法初阶:入门篇》😄
❤️【简介】:本课程是针对 Python 初学者设计的算法基础入门课程,涵盖算法概念、时间复杂度、空间复杂度等基础知识。通过实例演示线性搜索、二分搜索等算法,并介绍哈希表、深度优先搜索、广度优先搜索等搜索算法。此课程将为学员提供扎实的 Python 编程基础与算法入门,为解决实际问题打下坚实基础。
在这里插入图片描述

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【Java集合类面试二十九】、说一说HashSet的底层结构

文章底部有个人公众号&#xff1a;热爱技术的小郑。主要分享开发知识、学习资料、毕业设计指导等。有兴趣的可以关注一下。为何分享&#xff1f; 踩过的坑没必要让别人在再踩&#xff0c;自己复盘也能加深记忆。利己利人、所谓双赢。 面试官&#xff1a;说一说HashSet的底层结构…

【CCF-A类】IEEE-TRANS系列,1区顶刊,WOS稳定收录32年,对国人友好,仅17天检索!

论文写作堪比西天取经&#xff0c;当我们经历“九九八十一难&#xff0c;取得真经“&#xff0c;还有最关键的一步&#xff0c;就是选刊发表。是“投石问路”&#xff0c;还是“投其所好”&#xff1f; 选刊有多重要&#xff0c;相信只要有过发表SCI经验的人都十分清楚。如果不…

【QT】对象树

一、QT对象树的概念 先来看一下 QObject 的构造函数&#xff1a; 通过帮助文档我们可以看到&#xff0c;QObject 的构造函数中会传入一个 Parent 父对象指针&#xff0c;children() 函数返回 QObjectList。即每一个 QObject 对象有且仅有一个父对象&#xff0c;但可以有很多个…

什么是间谍软件恶意软件?

攻击者利用此类软件从受感染的设备中收集和传输信息。这可能包括个人、银行和用户凭证&#xff08;社交网络、流媒体服务、邮件等的登录名和密码&#xff09;&#xff0c;以及设备内存中的文件。 在间谍软件的帮助下&#xff0c;欺诈者还可以窃取公司凭证&#xff0c;不仅伤害…

Vue 3中toRaw和markRaw的使用

文章目录 Vue 3的响应性系统使用toRaw使用markRaw使用场景1. 与第三方库交互2. 提高性能3. 避免无限循环 总结 &#x1f389;欢迎来到Java学习路线专栏~探索Java中的静态变量与实例变量 ☆* o(≧▽≦)o *☆嗨~我是IT陈寒&#x1f379;✨博客主页&#xff1a;IT陈寒的博客&#…

Linux基础:2:shell外壳+文件权限

shell外壳文件权限 一.shell原理&#xff1a;1.对比&#xff1a;windo GUI 和 shell1.windo GUI2. shell 2.为什么&#xff1f;是什么&#xff1f;怎么办&#xff1f;1.为什么有shell2.是什么&#xff1f;3.怎么办&#xff1f;4.补充&#xff1a; 二.linux权限管理&#xff1a;…

Linux redis 安装

1、解压 tar -zxvf redis-5.0.10.tar.gz 2、cd /data/redis-5.0.10 文件夹 3、make 等待make命令执行完成即可。 make命令报错&#xff1a;cc 未找到命令&#xff0c;系统中缺少gcc&#xff0c;执行命令安装 gcc&#xff1a; yum -y install gcc automake autocon…

蓝桥杯每日一题2023.10.25

乘积尾零 - 蓝桥云课 (lanqiao.cn) 题目描述 题目分析 由于需要相乘的数很多&#xff0c;所以我们不能直接进行暴力模拟&#xff0c;我们知道10 2 * 5&#xff0c; 所以我们只需要找出这个数2和5的个数&#xff0c;其中2和5个数小的那个则为末尾0出现的个数 #include<bi…

探讨安科瑞低压备自投装置AM5-DB的应用-安科瑞 蒋静

1 概况 本项目主要为发电机组供电切换提供备自投保护功能&#xff0c;该发电机组的供电主要由两进线一母联的系统组成&#xff0c;其中&#xff0c;每路进线分别由一路市电和一路柴油发电机切换提供&#xff0c;故此&#xff0c;我司用了三台低压备自投装置AM5-DB来实现备自投…

软信天成:助力某制造企业建设产品主数据管理平台案例分享

某国有大型传统制造企业是一家跨领域、跨行业经营的国际化公司&#xff0c;在全球范围内拥有动力系统、工程机械、汽车制造等多个业务板块、分子公司遍及世界、产品远销110多个国家和地区&#xff0c;产品品类繁多&#xff0c;分支架构错综复杂。 近年来&#xff0c;数字化的深…

欢迎浪潮KaiwuDB成为开源社白金合作伙伴

众多开源爱好者翘首期盼的开源盛会&#xff1a;第八届中国开源年会&#xff08;COSCon23&#xff09;将于 10月28-29日在四川成都市高新区菁蓉汇举办。本次大会的主题是&#xff1a;“开源&#xff1a;川流不息、山海相映”&#xff01;各位新老朋友们&#xff0c;欢迎到成都&a…

Find My护照|苹果Find My技术与护照结合,智能防丢,全球定位

护照是一个国家的公民出入本国国境和到国外旅行或居留时&#xff0c; 由本国发给的一种证明该公民国籍和身份的合法证件。 护照&#xff08;PASSPORT&#xff09;一词在英文中是口岸通行证的意思。也就是说&#xff0c; 护照是公民旅行通过各国国际口岸的一种通行证明。 护照…

非对称加密---椭圆曲线---单向散列函数

4. 非对称加密 "非对称加密也叫公钥密码: 使用公钥加密, 使用私钥解密"在对称密码中&#xff0c;由于加密和解密的密钥是相同的&#xff0c;因此必须向接收者配送密钥。用于解密的密钥必须被配送给接收者&#xff0c;这一问题称为密钥配送问题。如果使用非对称加密也…

C语言求数组最小值,并返回下标

#include<stdio.h> #include<string.h> void main() {int a[] {12,5,21,33,55,77,11,2};int zf sizeof(a) / sizeof(a[0]);for (int i 0; i < zf; i){if (a[i] < a[0]){a[0] a[i];}}printf("最小为%d&#xff0c;下标是0",a[0]); } 如果是求最…

markdown操作

一、语法设置 1.1 标题 1.1.1 使用’#表示标题 #必须在行首&#xff0c;#越多&#xff0c;标题的级别越低1.2 代码块 1.2.1 行内代码块 使用反单引号&#xff08;一般在键盘的左上位置&#xff0c;和~是一个键&#xff09;来表示&#xff0c;如 hello&#xff1a;hello 1.2…

Windows一些基础设置

开机自启动 方法一&#xff1a; 1、首先按下键盘上的“Wini”打开设置窗口&#xff0c;在左边找到并进入“应用”&#xff1b; 2、接着在右侧点击并进入“启动”设置。 3、在启动应用下&#xff0c;将不需要开机自启动的软件给关掉。 方法二&#xff1a; 1、按CtrlShiftEs…

使用HXT和Haskell编写的程序

以下是一个使用HXT和Haskell编写的下载器程序&#xff0c;用于下载内容。此程序使用了proxy的代码。 -- 导入必要的库 import Network.HTTP.Conduit import Network.HTTP.Types.Status import Network.HTTP.Types.Header import Data.Conduit import Data.Conduit.Network imp…

Python 算法高级篇:布谷鸟哈希算法与分布式哈希表

Python 算法高级篇&#xff1a;布谷鸟哈希算法与分布式哈希表 引言 1. 什么是哈希算法&#xff1f;1.1 哈希算法的用途 2. 布谷鸟哈希算法2.1 布谷鸟哈希表的特点2.2 布谷鸟哈希算法的伪代码2.3 Python 中的布谷鸟哈希算法实现 3. 分布式哈希表3.1 分布式哈希表的特点3.2 一致性…

为啥外行都觉得程序员的代码不值钱?

点击下方“JavaEdge”&#xff0c;选择“设为星标” 第一时间关注技术干货&#xff01; 免责声明~ 任何文章不要过度深思&#xff01; 万事万物都经不起审视&#xff0c;因为世上没有同样的成长环境&#xff0c;也没有同样的认知水平&#xff0c;更「没有适用于所有人的解决方案…

根据输入类型来选择函数不同的实现方法functools.singledispatch

【小白从小学Python、C、Java】 【计算机等考500强证书考研】 【Python-数据分析】 根据输入类型来选择函数不同的实现方法 functools.singledispatch 输入6后&#xff0c;下列输出正确的是&#xff1f; from functools import singledispatch singledispatch def calcu…