记忆化搜索与动态规划:原理、实现与比较

        记忆化搜索和动态规划是解决优化问题的两种重要方法,尤其在处理具有重叠子问题和最优子结构性质的问题时非常有效。

目录

1. 记忆化搜索(Memoization)

定义:

实现步骤:

示例代码(斐波那契数列):

2. 动态规划(Dynamic Programming)

定义:

实现步骤:

示例代码(斐波那契数列):

3. 不同点与相同点

不同点:

相同点:

4. 联系与本质

联系:

本质:

5. 总结


1. 记忆化搜索(Memoization)

定义:

记忆化搜索是一种优化递归算法的方法,通过存储已经计算过的子问题的结果,避免重复计算。

实现步骤:

  1. 添加备忘录:通常使用数组或哈希表来存储已经计算过的结果。

  2. 递归返回时存储结果:在每次递归调用返回时,将结果存储在备忘录中。

  3. 递归前检查备忘录:在每次递归调用前,检查备忘录中是否已经有结果,如果有则直接返回。

示例代码(斐波那契数列):

#include <iostream>
#include <vector>
using namespace std;int fib(int n, vector<int>& memo) {if (n <= 1) return n;if (memo[n] != -1) return memo[n];memo[n] = fib(n-1, memo) + fib(n-2, memo);return memo[n];
}int main() {int n = 10;vector<int> memo(n+1, -1);cout << "Fibonacci number is " << fib(n, memo) << endl;return 0;
}

2. 动态规划(Dynamic Programming)

定义:

动态规划是一种将复杂问题分解为更简单的子问题的方法,通过填表的方式自底向上解决问题。

实现步骤:

  1. 确定状态表示:定义状态变量,如dp[i]表示第i个斐波那契数。

  2. 推导状态转移方程:如dp[i] = dp[i-1] + dp[i-2]

  3. 初始化:设置初始条件,如dp[0] = 0, dp[1] = 1

  4. 确定填表顺序:通常从左到右填写。

  5. 确定返回值:返回所需的结果,如dp[n]

示例代码(斐波那契数列):

#include <iostream>
#include <vector>
using namespace std;int fib(int n) {if (n <= 1) return n;vector<int> dp(n+1);dp[0] = 0;dp[1] = 1;for (int i = 2; i <= n; ++i) {dp[i] = dp[i-1] + dp[i-2];}return dp[n];
}int main() {int n = 10;cout << "Fibonacci number is " << fib(n) << endl;return 0;
}

3. 不同点与相同点

不同点:

  • 实现方式:记忆化搜索是自顶向下的递归方法,而动态规划是自底向上的递推方法。

  • 存储方式:记忆化搜索使用备忘录存储中间结果,动态规划使用表格存储状态。

  • 调用顺序:记忆化搜索依赖于递归调用,动态规划依赖于循环迭代。

相同点:

  • 优化目标:两者都旨在避免重复计算,提高算法效率。

  • 适用问题:都适用于具有重叠子问题和最优子结构性质的问题。

4. 联系与本质

联系:

  • 本质相同:两者都是对暴力解法的优化,通过存储中间结果来避免重复计算。

  • 相互转化:记忆化搜索可以看作是动态规划的递归实现,动态规划可以看作是记忆化搜索的迭代实现。

本质:

  • 暴力解法优化:两者都是对暴力解法的优化,通过存储已经计算过的值来减少计算量。

  • 重叠子问题:都利用了问题的重叠子问题性质,通过存储和重用子问题的解来提高效率。

5. 总结

        记忆化搜索和动态规划在本质上是相似的,都是通过存储中间结果来优化暴力解法。它们的主要区别在于实现方式和调用顺序。在实际应用中,选择哪种方法取决于具体问题的性质和编程习惯。理解它们的异同和联系,有助于更好地应用这些方法解决复杂的优化问题。

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

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Spring Boot 自动装配深度解析与实践指南

目录 引言&#xff1a;自动装配如何重塑Java应用开发&#xff1f; 一、自动装配核心机制 1.1 自动装配三大要素 1.2 自动装配流程 二、自定义自动配置实现 2.1 创建自动配置类 2.2 配置属性绑定 2.3 注册自动配置 三、条件注解深度应用 3.1 常用条件注解对比 3.2 自定…

关于常规模式下运行VScode无法正确执行“pwsh”问题

前言&#xff1a; pwsh在系统环境中正确配置&#xff0c;且可以运行在cmd&#xff0c; powshell&#xff08;5.1&#xff09;--- 都需要在管理员权限下运行 &#xff08;打开setting&#xff09; 打开setting.json &#xff08;在vscode中添加 powershell 7 路径&…

Ubuntu20.04双系统安装及软件安装(一):系统安装

Ubuntu20.04双系统安装及软件安装&#xff08;一&#xff09;&#xff1a;系统安装 Ubuntu系统卸载Ubuntu20.04安装BIOS进入系统安装 许久没写博客了&#xff0c;今天开始重新回归了。首先记录我在双系统上重装Ubuntu20.04的安装过程记录以及个人见解。 Ubuntu系统卸载 参考双…

基于CURL命令封装的JAVA通用HTTP工具

文章目录 一、简要概述二、封装过程1. 引入依赖2. 定义脚本执行类 三、单元测试四、其他资源 一、简要概述 在Linux中curl是一个利用URL规则在命令行下工作的文件传输工具&#xff0c;可以说是一款很强大的http命令行工具。它支持文件的上传和下载&#xff0c;是综合传输工具&…

开发博客系统

前言 准备工作 数据库表分为实体表和关系表 第一&#xff0c;建数据库表 然后导入前端页面 创建公共模块 就是统一返回值&#xff0c;异常那些东西 自己造一个自定义异常 普通类 mapper 获取全部博客 我们只需要返回id&#xff0c;title&#xff0c;content&#xff0c;us…

uniapp+vue3搭建项目

工具使用&#xff1a; Pinia Vue 3 官方推荐的状态管理库&#xff0c;比 Vuex 更轻量&#xff0c;支持模块化&#xff0c;结合 persistedstate 插件可以持久化存储数据。uView-plus 专为 UniApp 设计&#xff0c;支持 App、小程序、H5。UnoCSS 更轻量&#xff0c;比 TailwindCS…

如何通过rust实现自己的web登录图片验证码

在进行web系统开发时&#xff0c;为保障系统登录安全&#xff0c;登录页面中的验证码必不可少。在java中&#xff0c;我们可以利用相应的2D图像库快速生成图形验证码&#xff0c;而对于rust&#xff0c;我们没有合适的标准库进行图像验证码的生成。今天&#xff0c;我们通过使用…

Unity NGUI新手向几个问题记录

1.点Button没反应 制作Button组件时&#xff0c;不光要挂载Button脚本&#xff0c;还有挂载BoxCollider BoxCollider 接收事件 2.Button点击事件的增加与删除 使用.onClick.add增加事件&#xff0c;使用.onClick.Remove,.onClick.RemoveAt,onClick.RemoveRang,onClick.Clear移…

基于SpringBoot的“扶贫助农系统”的设计与实现(源码+数据库+文档+PPT)

基于SpringBoot的“扶贫助农系统”的设计与实现&#xff08;源码数据库文档PPT) 开发语言&#xff1a;Java 数据库&#xff1a;MySQL 技术&#xff1a;SpringBoot 工具&#xff1a;IDEA/Ecilpse、Navicat、Maven 系统展示 系统功能结构图 局部E-R图 系统首页界面 系统注册…

Rust编程实战:初探WebAssembly

WebAssembly: 网页应用的性能革命 ​互联网技术日新月异&#xff0c;Web应用已经从简单的网页跃升为功能丰富的平台。然而&#xff0c;JavaScript作为Web的主力语言&#xff0c;在处理计算密集型任务时仍然存在性能瓶颈。今天&#xff0c;我们来聊一聊可能改变Web格局的技术—…

蓝桥杯4T平台(串口打印电压值)

知识点&#xff1a;串口(单片机发送数据)按键ADC 题目 配置 代码 adc.c uint16_t getadc2(void) {uint16_t adc0;HAL_ADC_Start(&hadc2);adcHAL_ADC_GetValue(&hadc2);return adc; } adc.h uint16_t getadc2(void); main.c #include "lcd.h" #include…

【异常解决】Unable to start embedded Tomcat Nacos 启动报错

Unable to start embedded Tomcat Nacos 启动报错解决方案 一、背景描述二、原因分析三、解决方案 一、背景描述 Windows 本地启动 Nacos&#xff08;2.2.0&#xff09; 服务&#xff0c;控制台报错 Unable to start embedded Tomcat。 报错信息&#xff1a;Unable to star…

Spark核心之02:RDD、算子分类、常用算子

spark内存计算框架 一、目标 深入理解RDD弹性分布式数据集底层原理掌握RDD弹性分布式数据集的常用算子操作 二、要点 ⭐️1. RDD是什么 RDD&#xff08;Resilient Distributed Dataset&#xff09;叫做**弹性分布式数据集&#xff0c;是Spark中最基本的数据抽象&#xff0c…

Machine Learning 初探

前置知识 pandas 读取文件&#xff1a;read_csv查看信息 describe&#xff1a;查看整体信息&#xff0c;包括每列的平均值、最大最小值、标准差等head&#xff1a;输出头部几行数据columns&#xff1a;输出所有列名loc&#xff1a;查询数据&#xff0c;或是根据索引取对应的数…

linux第四讲----基础开发工具vim

1.软件安装 这里以ubuntu为例&#xff0c;安装sl软件,输入这个命令即可自动安装~ 使用一下&#xff0c;输入sl&#xff0c;屏幕上会出现一个移动的小火车 之后不想要了准备卸载就输入&#xff1a; 注意&#xff1a;1&#xff09;下载软件时也可以进行搜索~ 2&#xff09;cento…

【Wireshark 02】抓包过滤方法

一、官方教程 Wireshark 官网文档 &#xff1a; Wireshark User’s Guide 二、显示过滤器 2.1、 “数据包列表”窗格的弹出过滤菜单 例如&#xff0c;源ip地址作为过滤选项&#xff0c;右击源ip->prepare as filter-> 选中 点击选中完&#xff0c;显示过滤器&#…

在 macOS 使用 .pem 私钥免密登录腾讯云服务器

前言 在腾讯云上创建服务器时&#xff0c;如果选择了「密钥对」的登录方式&#xff0c;就会得到一个 .pem 文件作为私钥。很多小伙伴在使用 macOS 系统时&#xff0c;可能不清楚如何使用这个私钥文件来 SSH 免密登录远程服务器。本文将详细介绍如何在本地配置 .pem 私钥文件并…

Android U 分屏——SystemUI侧处理

WMShell相关的dump命令 手机分屏启动应用后运行命令&#xff1a;adb shell dumpsys activity service SystemUIService WMShell 我们可以找到其中分屏的部分&#xff0c;如下图所示&#xff1a; 分屏的组成 简图 分屏是由上分屏(SideStage)、下分屏(MainStage)以及分割线组…

【Python】——使用python实现GUI图书管理系统:Tkinter+SQLite实战

本文将通过一个完整的python项目——图书管理系统&#xff0c;演示如何利用Tkinter构建GUI 界面&#xff0c;结合SQLite数据库实现增删改查功能。代码简洁易懂&#xff0c;适合python初学者学习和二次开发。 一、项目功能概览 图书管理&#xff1a;添加、查看、修改、删除图书…

文件上传靶场(1--9关)

实验环境&#xff1a; 1&#xff0c;upload的靶场环境可以去GitHub上自行查找 2&#xff0c;打开小皮面板的nginx和数据库 3&#xff0c;将文件上传的靶场部署到本地&#xff1a; 放到小皮的phpstduy_pro的www下面 小提示&#xff1a; 另外如果你用的是php7的版本建议将版…