算法刷题-动态规划-1

news2024/7/4 5:16:53

算法刷题-动态规划-1

  • 不同路径
  • 不同路径||
    • 方法一:
    • 方法二
  • 第N个泰波那契数
    • 递归写法
    • 滚动数组
  • 三步问题
    • 递归操作
    • 滚动数组
  • 使用最小画法爬楼梯
    • 递归
  • 解码方法
    • 方法一
    • 方法二:(大佬讲解)

不同路径

在这里插入图片描述
在这里插入图片描述

//机器人不同的路径进入到指定的地点
public static int uniquepath(int m, int n) {
    if (m <= 0 || n <= 0)
    {
        return 0;
    }
    int[][] dp = new int[m][n];//初始化
   
    //如果只有i,j中有一个为0,那么机器人行走的方向只能有一种方式
    for (int i = 0; i < m; i++)
    {
        dp[i][0] = 1;
    }
    for (itn i = 0; i < n; i++)  
    {
        dp[0][i] = 1;  
    }
    //推导出dp[m-1][n-1],因为定义dp[i][j]就是表示的是在[i][j]点  
    //不同的路径的数目  
    for (itn i = 1; i < m; i++)    
    {
        for (int j = 1; j < n; j++)    
        {
            dp[i][j] = dp[i - 1][j] + dp[i][j - 1];    
        }
    }
    return dp[m - 1][n - 1];    

}

不同路径||

在这里插入图片描述

在这里插入图片描述
![在这里插入图片描述](https://img-blog.csdnimg.cn/55c59dbc1da64e20aed014ff76118002.png)

方法一:

大佬讲解
在这里插入图片描述

class Solution {
public:
    /**
     * 1. 确定dp数组下标含义 dp[i][j] 从(0,0)到(i,j)可能的路径种类;
     * 2. 递推公式 dp[i][j] = dp[i-1][j] + dp[i][j-1] 但是需要加限制条件就是没有障碍物的时候
     *    if(obstacleGrid[i][j] == 0) dp[i][j] = dp[i-1][j] + dp[i][j-1];
     * 3. 初始化 当obstacleGrid[i][j] == 0时,dp[i][0]=1 dp[0][i]=1 初始化横竖就可;
     * 4. 遍历顺序 一行一行遍历;
     * 5. 推导结果;
     */
    int uniquePathsWithObstacles(vector<vector<int>>& obstacleGrid) {
        /* 计算数组大小 */
        int m = obstacleGrid.size();
        int n = obstacleGrid[0].size();
        /* 定义dp数组 */
        vector<vector<int>> dp(m,vector<int>(n,0));
        /* 初始化dp数组 */
        for(int i = 0; i < m && obstacleGrid[i][0] == 0; i++)
            dp[i][0] = 1; 
        for(int i = 0; i < n && obstacleGrid[0][i] == 0; i++)   
            dp[0][i] = 1;      
        /* 一行一行遍历 */     
        for(int i = 1; i < m; i++) {     
            for(int j = 1; j < n; j++) {     
                /* 去除障碍物 */     
                if(obstacleGrid[i][j] == 1) continue;     
                
                dp[i][j] = dp[i-1][j] + dp[i][j-1];     
            }
        }
        return dp[m-1][n-1];     
    }
};


方法二

多加一行和一列的虚拟节点,防止出现越界的情况,
把它们初始化成0,但是要保证第一个节点初始化成1.
dp[0][1] = 1;


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


第N个泰波那契数

在这里插入图片描述


递归写法

1。先确定函数的一定是什么dp[ i ] 表示:第 i 个泰波那契数
2。题目中的关系代数是 dp[ i ] = dp[ i - 1 ] + dp[ i - 2 ] + dp[ i - 3。边界是T(0)=0,T(1)=1,T(2)=1T(0)=0, T(1)=1,
4。初始化为dp[ 0 ] = 0,dp[ 1 ] = 1,dp[ 2 ] = 1

class Solution {
public:
    int tribonacci(int n) {
        vector<int> dp(n + 1);

        if (n == 0) 
        {
            return 0;   
        }
        if (n <= 2)   
        {
            return 1;   
        }
        dp[0] = 0, dp[1] = 1, dp[2] = 1;   

        for (int i = 3; i <= n; i++) {   
            dp[i] = dp[i - 1] + dp[i - 2] + dp[i - 3];   
        }
        return dp[n];   
    }
};

滚动数组

class Solution {
public:
    int tribonacci(int n) {
        if (n == 0) {
            return 0;
        }
        if (n <= 2) {  
            return 1;  
        }

        int p = 0, q = 0, r = 1, s = 1;  

        for (int i = 3; i <= n; ++i) {  
            p = q;  
            q = r;  
            r = s;  
            s = p + q + r;  
        }
        return s;  
    }
};

三步问题

在这里插入图片描述

这就是老油条的步骤了,
先确定自己定义的函数,然后找出关系式,然后确定初始值

递归操作

class Solution {  
public:  
    int waysToStep(int n) {  
        vector<in#t> dp(n + 1);  
        const int MOD = 1e9 + 7;  
        //边界问题    
        if (n == 1 || n == 2) return n;    
        if (n == 3) return 4;    

        //初始化定义    
        dp[1] = 1, dp[2] = 2, dp[3] = 4;    

        for (int i = 4; i <= n; i++) {   
            dp[i] = ((dp[i - 3] + dp[i - 2]) % MOD + dp[i - 1]) % MOD;   
        }
        return dp[n];   
    }
};

滚动数组

class Solution {    
public:    
    int waysToStep(int n) {     
        int a=1,b=2,c=4,i;     
        for(i=2;i<=n;i++){     
            long long t=(a+b)%1000000007;     
            t=(t+c)%1000000007;     
            a=b;     
            b=c;     
            c=t;     
        }
        return a;     
    }
};

使用最小画法爬楼梯

在这里插入图片描述
在这里插入图片描述

题目要求的是到达第n级台阶楼层顶部的最小花费,可以用动态规划来解,下面一步一步来讲怎样确定状态空间、怎样给出状态转移方程。

递归

  1. 大佬讲解

  2. 最近的一步有两种情况,

  3. 从 dp[ i - 1 ] 走一步过来,支付cost[ i - 1 ] 的费用; 1. 从 dp[ i - 1 ] 走一步过来,支付cost[ i - 1 ] 的费用;

  4. 从 dp[ i - 2 ] 走两步过来,支付cost[ i - 2 ] 的费用。
    而 dp[ i ] 就是到达 i 位置的最小花费,
    那我们就能得出状态转移方程:
    dp [ i ] = min( dp[ i - 1 ] + cost[ i - 1 ],dp[ i - 2 ] + cost[ i - 2 ] )


class Solution {  
public:  
    int minCostClimbingStairs(vector<int>& cost) {  

        int n = cost.size();  

        // 创建dp表,这样初始化默认填充的是 0   
        vector<int> dp(n + 1);  

       
        for (int i = 2; i <= n; i++) {  
            dp[i] = min(dp[i - 1] + cost[i - 1], dp[i - 2] + cost[i - 2]);  
        }

        return dp[n];  
    }
};

解码方法

在这里插入图片描述

在这里插入图片描述

方法一

动态规划的使用:
1。确立dp 数组的定义,代表的是 dp[i] 位置代表的是第i个位置时候解码方法的总数。
2。找关系代数=

  1. s[ i ] 单独解码,如果是单独解码,当 s[ i ] 的值是 1~9 的时候可以自己解码,
    自己解码的方案数就是 dp[ i - 1 ],如果 s[ i ] 的值是 0,那方案数就是0,整体解码失败,

  2. s[ i ] 和 s[ i - 1 ] 一起解码,当 s[ i - 1 ] * 10 + s[ i ] 的值是 10~26 的时候就可以解码,
    而解码数就是 dp[ i - 2 ],如果解码失败,不在这个区间内,那方案数就也是0。
    3。初始化dp数组,
    初始化 dp[ 0 ] 和 dp[ 1 ] 位置,
    dp[ 0 ] 位置,如果s[ 0 ] 解码成功就是1,不成功就是0
    dp[ 1 ] 位置,如果 dp[ 1 ] 能自己解码,就 + 1,如果能跟 dp[ 0 ] 一起解码,就再 + 1,
    如果dp[ 1 ] 两种情况都不能解码,就是0。(所以可能是0, 1, 2)

class Solution {
public:
    int numDecodings(string s) {
        int n = s.size();
        vector<int> dp(size);

        dp[0] = s[0] != '0';
        if (size == 1) return dp[0];

        if (s[0] != '0' && s[1] != '0') dp[1]++;
        int t = (s[0] - '0') * 10 + (s[1] - '0');

        if (t >= 10 && t <= 26) dp[1]++;

        for (int i = 2; i < size; i++) {
            if (s[i] != '0') dp[i] += dp[i - 1]; 

            t = (s[i - 1] - '0') * 10 + (s[i] - '0');
            if (t >= 10 && t <= 26) dp[i] += dp[i - 2]; //一起解码
        }
        return dp[n - 1];
    }
};

方法二:(大佬讲解)

在这里插入图片描述

class Solution {
public:
    int numDecodings(string s) {
        if (s[0] == '0') return 0;
        int n = s.size();
        vector<int> dp(n + 1, 1);
        //dp[0]表示s[-1]的状态, dp[1] 表示 s[0]的状态
        //dp[i] 表示 s[i-1]的状态
        for (int i = 2; i <= n; i++) {
            if (s[i - 1] == '0') {
                if (s[i - 2] == '1' || s[i - 2] == '2')//唯一译码,不增加情况
                    dp[i] = dp[i - 2]; 
                else//这里要好好理解一下,比如给定340, 输出可行的编码数为0, 因为0和40都无法转换  
                    return 0;  
            }
            else if (s[i - 2] == '1' || s[i - 2] == '2' && s[i - 1] >= '1' && s[i - 1] <= '6')


                dp[i] = dp[i - 1] + dp[i - 2];  
            else//当上述条件都不满足,维持上一个状态  
                dp[i] = dp[i - 1];  
        }
        //for(auto c:dp) cout << c << ",";  
        return dp[n];//返回dp[n] 即最后 s[n-1] 的状态  
    }
};

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

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

相关文章

909-2015-T3

文章目录 1.原题2.算法思想2.1.求树的高度2.2.求路径 3.关键代码4.完整代码5.输出结果 1.原题 试编写算法&#xff0c;求给定二叉树上从根节点到叶子节点的一条路径长度等于树的深度减一的路径&#xff08;即列出从根节点到该叶子节点的节点序列&#xff09;&#xff0c;若这样…

【JavaEE】Spring更简单的存储和获取对象(类注解、方法注解、属性注入、Setter注入、构造方法注入)

一、存储Bean对象 在这篇文章中我介绍了Spring最简单的创建和使用&#xff1a;Spring的创建和使用 其中存储Bean对象是这样的&#xff1a; 1.1 配置扫描路径 想要成功把对象存到Spring中&#xff0c;我们需要配置对象的扫描包路径 这样的话&#xff0c;就只有被配置了的包…

STM32F103C8T6第5天:独立看门狗、窗口看门狗、dma实验

1. 独立看门狗IWDG介绍&#xff08;341.45&#xff09; 什么是看门狗&#xff1f; 在由单片机构成的微型计算机系统中&#xff0c;由于单片机的工作常常会受到来自外界电磁场的干扰&#xff0c;造成程序的跑飞&#xff0c;而陷入死循环&#xff0c;程序的正常运行被打断&#…

引爆关注,聚焦上海新闻媒体邀请

传媒如春雨&#xff0c;润物细无声&#xff0c;大家好&#xff0c;我是51媒体网胡老师。 上海拥有众多的新闻媒体机构&#xff0c;包括报纸、电视、广播和网络媒体等。这些媒体在报道国内外新闻、传播信息等方面发挥着重要作用。 其中&#xff0c;上海电视台是上海最大的电视…

使用VSCode+PlatformIO搭建ESP32开发环境

Arduino IDE本来就是为创客们开发的&#xff0c;虽然没代码提示功能&#xff0c;文件的关系也不清晰&#xff0c;函数不能跳转&#xff0c;头文件也打不开&#xff0c;但人家的初衷就是为了简单而生的&#xff1b;但还是有一些同学喜欢高级点的IDE&#xff0c;也没问题&#xf…

详解Python中哈希表的使用。站在开发者角度,与大家一起探究哈希的世界。

文章目录 1. 前言2. 哈希表2.1 哈希函数2.2 哈希算法2.3 常见哈希算法2.4 哈希冲突 3.总结关于Python技术储备一、Python所有方向的学习路线二、Python基础学习视频三、精品Python学习书籍四、Python工具包项目源码合集①Python工具包②Python实战案例③Python小游戏源码五、面…

算法设计与分析复习--分支界限法

文章目录 上一篇分支界限法性质装载问题0-1背包问题单源最短路问题最大团问题下一篇 上一篇 算法设计与分析复习–回溯法&#xff08;二&#xff09; 分支界限法性质 分支界限法是按广度优先策略或最小耗费优先遍历问题的解空间树。 搜索解空间&#xff1a; 子集树排列树 …

2024贵州大学计算机考研分析

24计算机考研|上岸指南 贵州大学 贵州大学计算机科学与技术学院&#xff08;贵州大学省级示范性软件学院&#xff09;位于贵州省贵阳市花溪区贵州大学东校区。 计算机科学与技术学院&#xff08;软件学院&#xff09;自1972年创办计算机软件本科专业开始&#xff0c;至今已有…

sso 四种授权模式

单点登录 单点登录&#xff0c;英文是 Single Sign On&#xff08;缩写为 SSO&#xff09;。即多个站点共用一台认证授权服务器&#xff0c;用户在站点登录后&#xff0c;可以免登录访问其他所有站点。而且&#xff0c;各站点间可以通过该登录状态直接交互。例如&#xff1a; …

aspera替代方案,镭速大文件传输解决方案替代

相信不少的互联网用户对于传输软件aspera并不陌生&#xff0c;但是市面上有没有哪一些aspera替代方案&#xff0c;aspera替代方案是否比aspera更加能够解决数据传输的需求&#xff0c;是一个值得思考的事情&#xff0c;那么我们先来了解一下aspera以及aspera替代方案。 了解Asp…

[Linux] shell条件语句和if语句

一、条件语句 1.1 测试 test 测试文件的表达式是否成立 格式&#xff1a;test 条件表达式 [ 条件表达式 ] 选项作用-d测试是否为目录-e测试目录或文件是否存在-a测试目录或文件是否存在-f测试是否为文件-r测试当前用户是否有权限读取-w测试当前用户是否有权限写入-x测试当前…

csdn最新最全pytest系列——pluggy插件源码解读(一)HookspecMarker类和HookimplMarker类分析

简介 pluggy是一个非常优秀的插件系统&#xff0c;它是理解pytest的核心&#xff0c;只有理解了pluggy的原理&#xff0c;才能更好的理解和使用pytest&#xff0c;否则见到了pytest的很多应用都会感觉很难理解 pluggy插件总共的代码量不足一千行&#xff0c;而实现的功能却是…

SpringBoot : ch06 整合 web (一)

前言 SpringBoot作为一款优秀的框架&#xff0c;不仅提供了快速开发的能力&#xff0c;同时也提供了丰富的文档和示例&#xff0c;让开发者更加容易上手。在本博客中&#xff0c;我们将介绍如何使用SpringBoot来整合Web应用程序的相关技术&#xff0c;并通过实例代码来演示如何…

Axios简单使用与配置安装-Vue

安装Axios npm i axios main.js 导入 import Axios from axios Vue.prototype.$axios Axios简单发送请求 get getTest() {this.$axios({method: GET,url: https://apis.jxcxin.cn/api/title?urlhttps://apis.jxcxin.cn/}).then(res > {//请求成功回调console.log(res)}…

使用ChatGPT创建Makefile构建系统:使用Make运行Docker

使用ChatGPT创建Makefile构建系统&#xff1a;使用Make运行Docker 芯语芯愿&#xff08;知乎/纷传/CSDN/&#xff09;&#xff1b;小石头的芯语芯愿&#xff08;微信公众号&#xff09; 开发高效现代的构建系统对于满足开发周期需求至关重要。原先&#xff0c;嵌入式开发者一…

多选按钮关联多个el-checkbox-group

需求&#xff1a; 如图设计稿&#xff0c;全部企业成员下面的数据来源与两个接口&#xff0c;点击全部企业成员需要勾选全部&#xff0c;下面选中全部企业成员要是选中状态&#xff0c;所以需要两个数组变量&#xff0c;两个el-checkbox-group来控制&#xff1b;有人可能会疑问…

Git远程库操作(GitHub)

GitHub 网址&#xff1a;https://github.com/ 创建远程仓库 远程仓库操作 命令名称作用git remote -v查看当前所有远程地址别名git remote add 别名 远程地址起别名git push 别名 分支推送本地分支上的内容到远程仓库git clone 远程地址将远程仓库的内容克隆到本地git pull 别…

OSG文字-HUD显示汉字示例(3)

显示文字是一种非常实用的技术&#xff0c;可以用来把一些重要的文字始终显示在屏幕上。HUD的全称是HeadsUpDisplay&#xff0c;即抬头显示&#xff0c;这种技术最早应用在军事战斗机上。 创建HUD显示的基本步骤如下: <1> 创建一个osg::Camera对象&#xff0c;设置视图、…

利用QRCode.js生成动态二维码页面

文章目录 QRCode.js简介HTML结构JavaScript生成动态二维码拓展功能1. 联系信息二维码2. Wi-Fi网络信息二维码 总结 &#x1f389;利用QRCode.js生成动态二维码页面 ☆* o(≧▽≦)o *☆嗨~我是IT陈寒&#x1f379;✨博客主页&#xff1a;IT陈寒的博客&#x1f388;该系列文章专栏…

接口自动化测试实战经验分享,测试用例也能自动生成

作为测试&#xff0c;你可能会对以下场景感到似曾相识&#xff1a;开发改好的 BUG 反复横跳&#xff1b;版本兼容逻辑多&#xff0c;修复一个 BUG 触发了更多 BUG&#xff1b;上线时系统监控毫无异常&#xff0c;过段时间用户投诉某个页面无数据&#xff1b;改动祖传代码时如履…