DP:解决路径问题

news2024/12/22 20:43:26

文章目录

  • 二维DP模型
  • 如何解决路径问题
  • 有关路径问题的几个问题
    • 1.不同路径
    • 2.不同路径Ⅱ
    • 3.下降路径最小和
    • 4.珠宝的最高价值
    • 5.地下城游戏
  • 总结

在这里插入图片描述

二维DP模型

二维动态规划(DP)模型是一种通过引入两个维度的状态和转移方程来解决复杂问题的技术。它在许多优化和组合问题中广泛应用,尤其是那些需要考虑二维数组或矩阵的情况。

以下是二维DP模型的核心概念和步骤:

  1. 状态定义:二维DP模型使用一个二维数组(或矩阵)来表示问题的状态。每个状态通常由两个变量(例如i和j)表示,表示在问题空间中的某个位置或状态。

  2. 状态转移方程:这是DP的核心。它描述了如何从一个状态转移到另一个状态,通常是通过递推关系来实现。转移方程基于问题的具体特性进行设计。

  3. 初始状态和边界条件:在DP表格中需要明确初始状态和边界条件。这些条件为DP表格的填充提供了起点。

  4. 目标状态:最后,我们通过目标状态来得到问题的最终解。通常是二维数组中的一个或几个特定位置。

如何解决路径问题

路径问题是动态规划中非常经典的一类问题,通常涉及从一个起点到一个终点的最短路径、最大路径或独特路径数等。解决路径问题的常用方法包括递归、回溯和动态规划(DP)。其中,动态规划由于其效率和易理解性,成为解决路径问题的常用技术。以下是解决路径问题的一些常见步骤和示例:

一般步骤

  1. 定义状态:确定DP数组的含义,通常是定义dp[i][j]表示从起点到位置(i, j)的某种路径属性(如路径和、路径数等)。

  2. 状态转移方程:建立递推关系,描述如何从一个状态转移到另一个状态。

  3. 初始化:根据问题的具体情况,设置DP数组的初始值。

  4. 计算DP数组:按照状态转移方程填充DP数组。

  5. 提取结果:通过DP数组得到最终结果。

有关路径问题的几个问题

1.不同路径

题目链接
题目:

在这里插入图片描述

样例输出和输入:

在这里插入图片描述

这道题是一个很典型的二维DP问题,也是二维DP中的路径问题的一种,这道题给定一个宽是m,长是n,让我们求在这个二位数组中从[0,0]点到[m-1,n-1]的方法有多少种。
在这里插入图片描述

算法原理:
算法原理也和传统的DP问题的步骤是一样的。
第一步:状态表示,先确定dp表是初始位置还是 末位置,很显然这道题要我们求的是方法有多少种,dp肯定是末位置,所以这里dp[i][j]到达[i,j]位置时有多少种方法。
第二步:状态转移方程,这道题dp表示的是到达某位置时的方法的种数,
在这里插入图片描述
很显然这道题题目要求只能向下或者向右移动,所以我们只有可能从[i,j]位置的上方或者[i,j]的左方到达[i,j]位置,所以我们需要求[i,j]位置的最多的方法数,只需要求出左边和上面的方法总数之和即可。
状态转移方程:dp[i][j]=dp[i-1][j]+dp[i][j-1]
第三步:初始化问题,这道题的当前数据需要用到左边的数据和上面的数据,所以这道题越界的地方应该是红色的地方:在这里插入图片描述
处理这种越界情况我们初始化只需要多开辟一行一列数组:
在这里插入图片描述
这样就不会出现越界的情况了,初始化应该把蓝色的部分全部初始化掉,具体初始哈为多少了,首先这相当于是一个虚拟的节点,为了防止越界而产生的,所以先初始化为0,但是如果初始化为零那么总的方法数就是零了,所以我们需要把[0,1]位置或者[1,0]位置初始化为1.
第四步:填表顺序,这道题很显然是从左上角开始 按顺序遍历。
第五步:返回值问题,这道题求的是到达左下角的方法总数,所以是返回dp[m][n]。

代码展示:

class Solution {
public:
    int uniquePaths(int m, int n) 
    {
        //创建一个dp表,第一排和第一列表示虚拟节点
        vector<vector<int>> dp(m+1,vector<int>(n+1,0));
        //初始化[0,1]节点
        dp[0][1]=1;
        //填表
        for(int i=1;i<m+1;i++)
        {
            for(int j=1;j<n+1;j++)
            {
                //状态转移方程
                dp[i][j]=dp[i-1][j]+dp[i][j-1];
            }
        }
        //返回值
        return dp[m][n];
    }
};

运行结果:
在这里插入图片描述

2.不同路径Ⅱ

题目链接
题目:

在这里插入图片描述

样例输出和输入:

在这里插入图片描述

算法原理:
这道题和上一道题其实是一样的,只需要加一个判断,如果obstacleGrid数组中的值是1的话当前方法数就是0,所以在上道题的条件下加一个if条件的判断即可 。
代码展示:

class Solution {
public:
    int uniquePathsWithObstacles(vector<vector<int>>& obstacleGrid) {
        int m=obstacleGrid.size();
        int n=obstacleGrid[0].size();
        vector<vector<int>> dp(m+1,vector<int>(n+1,0));
        dp[0][1]=1;
        for(int i=1;i<m+1;i++)
        {
            for(int j=1;j<n+1;j++)
            {
                if(obstacleGrid[i-1][j-1]==0)
                {
                    dp[i][j]=dp[i-1][j]+dp[i][j-1];
                }
            }
        }
        return dp[m][n];
    }
};

运行结果:
在这里插入图片描述

3.下降路径最小和

题目链接
题目:

在这里插入图片描述

样例输出和输入:

在这里插入图片描述

这道题的题意很简单,我们首先可以在一个n*n的矩阵的第一行 选三个数
在这里插入图片描述
当我们选中间的格子时,可以下降的格子,我们假设当前格子的下标是[i,j],则可以访问的下一行的下降的格子应该是:[i+1,j-1] [i+1,j] [i+1,j+1]这三个下标,这道题让 我们求的就是到达最后一行的时候下降的最小的路径和,每个方格中的值就表示当前格子的路径数,所以当到达最后一行的时候走过的路径和就是走过的所有格子的值的和。
算法原理:
第一步:状态表示,这道题根据问题我们就知道这道题求的是下降路径最小和,所以我们的dp[i][j]表示的是到达[i][j]位置的时候的当前最小和。
第二步:状态转移方程,我们假设一个格子的下标是[i,j]。
在这里插入图片描述

[i,j]的最小下降路径是不是应该等于上面三个的相邻的格子的最小路径加上当前格子的值。
所以状态转移方程应该是:dp[i][j]=min(dp[i-1][j],dp[i-1][j-1],dp[i-1][j+1])+matrix[i][j]
第三步:初始化为题,其实初始化还是和上面的一样,但是因为我们要用到上一行左边和右边的格子,所以这里会出现越界的格子不止左边和上面的格子还有右边的格子
在这里插入图片描述
所以我们开辟空间应该这样开辟:
在这里插入图片描述
初始化应该初始化蓝色格子,由于当我们请求[i,j-1]位置的最小路径和的时候最左边的一列会影响最小值的大小,,所以这里初始化不能初始化为零,应该初始化为正无穷(INT_MAX)右边的蓝色格子也 应该初始化为正无穷,但是上面一排的格子应该初始化为0,这样才不会影响结果。
第四步:填表顺序,填表 顺序按顺序遍历。
第五步 :返回值,由于这道题求的是最小路径和,所以应该返回dp数组中最后一行中的最小值。
代码展示:

class Solution {
public:
    int minFallingPathSum(vector<vector<int>>& matrix) {
        int m=matrix.size();
        int n=matrix[0].size();
        vector<vector<int>> dp(m+1,vector<int>(n+2,INT_MAX));
        for(int j=0;j<n+2;j++)
        {
            dp[0][j]=0;
        }
        for(int i=1;i<m+1;i++)
        {
            for(int j=1;j<n+1;j++)
            {
                dp[i][j]=min(min(dp[i-1][j-1],dp[i-1][j]),dp[i-1][j+1])+matrix[i-1][j-1];
            }
        }
        int Min=INT_MAX;
        for(int j=0;j<n+2;j++)
        {
            Min=min(Min,dp[m][j]);
        }
        return Min;
    }
};

运行结果:
在这里插入图片描述

4.珠宝的最高价值

题目链接
题目:

在这里插入图片描述

样例输出和输入:

在这里插入图片描述

这道题让我们求出珠宝的最高价值,
在这里插入图片描述
很显然根据示例一种的例子,价值最高的珠宝应该是这条路线之和,然后返回
算法原理:
状态表示:dp[i][j]当前位置的珠宝的最高价值。
状态转移方程:max(dp[i-1][j]+frame[i-1][j-1],dp[i][j-1]+frame[i-1][j-1])
初始化:初始化 应该初始化最左边和最上面,初始化为零,因为当前的礼物价值是0.
代码展示:

class Solution {
public:
    int jewelleryValue(vector<vector<int>>& frame) {
        int m=frame.size();
        int n=frame[0].size();
        vector<vector<int>> dp(m+1,vector<int>(n+1,0));
        for(int i=1;i<m+1;i++)
        {
            for(int j=1;j<n+1;j++)
            {
                dp[i][j]=max(dp[i-1][j]+frame[i-1][j-1],dp[i][j-1]+frame[i-1][j-1]);
            }
        }
        return dp[m][n];
    }
};

运行结果:
在这里插入图片描述

5.地下城游戏

题目链接
题目:

在这里插入图片描述

样例输出和输入:

在这里插入图片描述

这道题让我们求出就出公主需要的最小健康值,当我们找到最小的一个路径的和加上1就是需要的最小的健康值。
算法原理:
状态表示:dp[i][j]表示当前位置救出公主需要的最小的健康程度,所以这道题的dp[i][j]应该是起点,而不是终点。
状态转移方程:我们设当前位置的最小的健康程度是dp[i][j],则当我们用dp[i][j]-dungeon[i][j]>=dp[i+1][j],同理还有一种情况:dp[i][j]-dungeon[i][j]>=dp[i][j+1]所以最小的健康程度应该是求一个最小值,则状态转移方程:dp[i][j]=min(dp[i+1][j],dp[i][j+1])-dungeon[i][j],但是需要注意的是如果dungeon是一个很大的正值的时候,会出现负数,由于这道题的题目要求是最低的健康值是1,到0或者小于零就死了,所以这道题不能出现负数,所以应该和1取一下max。
初始化,初始化我们和以前不一样,应该:
在这里插入图片描述
应该初始化左下角,由于取的最小值,所以不能初始化为0,应该初始化为INT_MAX,但是公主下面的和右边的格子应该初始化为1,因为救完公主的最小健康值是1,所以应该初始化为1.
填表顺序:从右下角倒着填表
返回值:返回dp数组的第一个值。
代码展示:

class Solution {
public:
    int calculateMinimumHP(vector<vector<int>>& dungeon) 
    {
        int m=dungeon.size();
        int n=dungeon[0].size();
        vector<vector<int>> dp(m+1,vector<int>(n+1,INT_MAX));
        dp[m][n-1]=1;
        dp[m-1][n]=1;
        for(int i=m-1;i>=0;i--)
        {
            for(int j=n-1;j>=0;j--)
            {
                dp[i][j]=min(dp[i+1][j],dp[i][j+1])-dungeon[i][j];
                dp[i][j]=max(dp[i][j],1);
            }
        }
        return dp[0][0];
    }
};

运行结果:
在这里插入图片描述

总结

在这篇博客中,我们详细探讨了动态规划(DP)在解决路径问题中的应用。我们首先回顾了动态规划的基本概念和其核心思想,即通过将问题分解为更小的子问题并存储其结果来避免重复计算。然后,我们通过多个经典的路径问题示例,如最短路径问题、最长路径问题和独特路径问题,展示了如何将动态规划技术应用于实际问题中。

通过这些示例,我们可以看到,动态规划不仅提高了算法的效率,还提供了一种系统化的思维方式,使我们能够更加清晰地理解和解决复杂的路径问题。掌握动态规划技巧,不仅有助于我们在学术研究中取得突破,还能在实际工程项目中大幅度提高解决问题的能力。

希望通过这篇博客,读者们能够更好地理解动态规划的基本原理和应用场景,并在未来的学习和工作中灵活运用这一强大的工具。感谢阅读,如果您有任何问题或建议,欢迎在评论区与我交流。

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

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

相关文章

SpringBoot: Eureka入门

1. IP列表 公司发展到一定的规模之后&#xff0c;应用拆分是无可避免的。假设我们有2个服务(服务A、服务B)&#xff0c;如果服务A要调用服务B&#xff0c;我们能怎么做呢&#xff1f;最简单的方法是让服务A配置服务B的所有节点的IP&#xff0c;在服务A内部做负载均衡调用服务B…

跟《经济学人》学英文:2024年6月22日这期 India’s electronics industry is surging

India’s electronics industry is surging Foreign and domestic firms are investing in local manufacturing surge:激增&#xff1b;急剧上升&#xff1b; 原文&#xff1a; To witness India’s growing role as a manufacturing hub, dodge Bangalore’s notorious t…

FreeBSD虚拟化解决之道:高效、安全、灵活的虚拟解决方案全览

FreeBSD下的虚拟化技术 虚拟化软件可让一台计算机同时运行多个操作系统。这种用于个人电脑的系统软件通常涉及一个运行虚拟化软件的宿主机&#xff08;host&#xff09;操作系统&#xff0c;并支持任何数量的客户机&#xff08;guest&#xff09;操作系统。 FreeBSD下的虚拟解…

惠海H6392 2.6v升5V 3.7V升9V 4.2V升12V 升压恒压芯片 小家电IC

惠海H6392升压恒压芯片是一款小家电、移动设备以及其他需要升压恒压电源的电子设备设计的DC-DC转换器。这款芯片以其独特的产品特性和广泛的应用场景&#xff0c;为电子产品设计者提供了高效、稳定的电源解决方案。 产品描述&#xff1a; H6392采用了简单的电流模式升压技术&a…

数据质量管理-时效性管理

前情提要 根据GB/T 36344-2018《信息技术 数据质量评价指标》的标准文档&#xff0c;当前数据质量评价指标框架中包含6评价指标&#xff0c;在实际的数据治理过程中&#xff0c;存在一个关联性指标。7个指标中存在4个定性指标&#xff0c;3个定量指标&#xff1b; 定性指标&am…

【漏洞复现】科立讯通信有限公司指挥调度管理平台uploadgps.php存在SQL注入

0x01 产品简介 科立讯通信指挥调度管理平台是一个专门针对通信行业的管理平台。该产品旨在提供高效的指挥调度和管理解决方案&#xff0c;以帮助通信运营商或相关机构实现更好的运营效率和服务质量。该平台提供强大的指挥调度功能&#xff0c;可以实时监控和管理通信网络设备、…

文件加密|电脑文件夹怎么设置密码?5个文件加密软件,新手必看!

电脑文件夹怎么设置密码&#xff1f;您是否希望更好地在电脑上保护您的个人或敏感文件&#xff1f;设置电脑文件夹密码是一种简单而有效的方式来确保你的隐私不被侵犯。通过使用文件加密软件&#xff0c;您可以轻松地为您的文件和文件夹设置密码保护。因此&#xff0c;本文将介…

4.x86游戏实战-人物状态标志位

免责声明&#xff1a;内容仅供学习参考&#xff0c;请合法利用知识&#xff0c;禁止进行违法犯罪活动&#xff01; 本次游戏没法给 内容参考于&#xff1a;微尘网络安全 上一个内容&#xff1a;3.x86游戏实战-寄存器 人物状态标志位&#xff1a; 什么叫人物状态标志位&…

【机器学习】大模型训练的深入探讨——Fine-tuning技术阐述与Dify平台介绍

目录 引言 Fine-tuning技术的原理阐 预训练模型 迁移学习 模型初始化 模型微调 超参数调整 任务设计 数学模型公式 Dify平台介绍 Dify部署 创建AI 接入大模型api 选择知识库 个人主页链接&#xff1a;东洛的克莱斯韦克-CSDN博客 引言 Fine-tuning技术允许用户根…

pytorch-01

加载mnist数据集 one-hot编码实现 import numpy as np import torch x_train np.load("../dataset/mnist/x_train.npy") # 从网站提前下载数据集&#xff0c;并解压缩 y_train_label np.load("../dataset/mnist/y_train_label.npy") x torch.tensor(y…

【单片机毕业设计11-基于stm32c8t6的智能水质检测】

【单片机毕业设计11-基于stm32c8t6的智能水质检测】 前言一、功能介绍二、硬件部分三、软件部分总结 前言 &#x1f525;这里是小殷学长&#xff0c;单片机毕业设计篇11基于stm32的智能水质检测系统 &#x1f9ff;创作不易&#xff0c;拒绝白嫖可私 一、功能介绍 -------------…

基于VMware的linux操作系统安装(附安装包)

目录 一、linux操作系统下载链接 二、开始导入镜像源 注&#xff1a;若是还没安装VMware请转到高效实现虚拟机&#xff08;VMware&#xff09;安装教程&#xff08;附安装包&#xff09;-CSDN博客 一、linux操作系统下载链接 1.官网链接下载 ubuntu&#xff1a;ubuntu官网…

连环计 | 第6集 | 百姓有倒悬之危,君臣有累卵之急 | 貂蝉 | 三国演义 | 逐鹿群雄

&#x1f64b;大家好&#xff01;我是毛毛张! &#x1f308;个人首页&#xff1a; 神马都会亿点点的毛毛张 &#x1f4cc;这篇博客分享的是《三国演义》文学剧本第Ⅰ部分《群雄逐鹿》的第6️⃣集《连环计》的经典语句和文学剧本全集台词 文章目录 1.经典语句2.文学剧本台词 …

【Spring Boot】Java 的数据库连接模板:JDBCTemplate

Java 的数据库连接模板&#xff1a;JDBCTemplate 1.JDBCTemplate 初识1.1 JDBC1.2 JDBCTemplate 2.JDBCTemplate 实现数据的增加、删除、修改和查询2.1 配置基础依赖2.2 新建实体类2.3 操作数据2.3.1 创建数据表2.3.2 添加数据2.3.3 查询数据2.3.4 查询所有记录2.3.5 修改数据2…

AXI接口简介

AXI接口&#xff0c;全称为Advanced eXtensible Interface&#xff0c;是ARM公司推出的一种高性能、低成本、可扩展的高速总线接口。AXI接口是ARM公司提出的AMBA&#xff08;Advanced Microcontroller Bus Architecture&#xff09;高级微控制器总线架构的一部分。2003年发布了…

List接口, ArrayList Vector LinkedList

Collection接口的子接口 子类Vector&#xff0c;ArrayList&#xff0c;LinkedList 1.元素的添加顺序和取出顺序一致&#xff0c;且可重复 2.每个元素都有其对应的顺序索引 方法 在index 1 的位置插入一个对象&#xff0c;list.add(1,list2)获取指定index位置的元素&#…

Lr、LrC软件下载安装 Adobe Lightroom专业摄影后期处理软件安装包分享

Adobe Lightroom它不仅为摄影师们提供了一个强大的照片管理平台&#xff0c;更以其出色的后期处理功能&#xff0c;成为了摄影爱好者们争相追捧的必备工具。 在这款软件中&#xff0c;摄影师们可以轻松地管理自己的照片库&#xff0c;无论是按拍摄日期、主题还是其他自定义标签…

LONGAGENT:优化大模型处理长文本

现有的大模型&#xff08;LLMs&#xff09;&#xff0c;尽管在语言理解和复杂推理任务上取得了显著进展&#xff0c;但在处理这些超长文本时却常常力不从心。它们在面对超过10万令牌的文本输入时&#xff0c;常常会出现性能严重下降的问题&#xff0c;这被称为“中间丢失”现象…

安全与加密常识(0)安全与加密概述

文章目录 一、信息安全的基本概念二、加密技术概述三、常见的安全协议和实践四、加密的挑战与应对 在数字时代&#xff0c;信息安全和加密已成为保护个人和企业数据不受侵犯的关键技术。本文将探讨信息安全的基础、加密的基本原理&#xff0c;以及实用的保护措施&#xff0c;以…

Installed Build Tools revision xxx is corrupted. Remove and install again 解决

1.在buildTools文件下找到对应的sdk版本&#xff0c;首先将版本对应目录下的d8.bat改名为dx.bat。 2.在lib文件下将d8.jar改名为dx.jar。 3.重新编译工程即可