初闻动态规划

前言

本文以一道常见的算法面试题开篇,引入动态规划的基础概念, 介绍其思考过程。

正文

一、常见的一道算法面试题——上台阶

有一个楼梯总共n个台阶,只能往上走,每次只能上1个、2个台阶,总共有多少种走法。

解决方案

1、排列组合;

枚举2的个数,再枚举2具体放的位置;

计算复杂,容易遗漏。

2、动态规划;

dp[n] 表示n个台阶的走法,那么有:

dp[n]=dp[n-1]+dp[n-2];

思路清晰,代码简单。

二、动态规划基础概念

1、动态规划;

动态规划(Dynamic Programming)指的是解最优化问题的一种方法。

2、最优子结构性质;

问题的最优解可以分解为若干子问题,且子问题的解也是最优的;

以上台阶为例,到第i层的最多走法,可以分解为第i-1层和第i-2层的走法之和,且第i-1层和第i-2层的走法也是最多的;

3、 无后效性;

现阶段的决策不会影响未来的决策;

以上台阶为例,走到第i-2层的最多走法,不会因为增加第i-1层而改变;

三、动态规划思考过程

动态规划的思考过程可以总结为:大事化小,小事化了

大事化小

一个较大的问题,通过找到与子问题的重叠,把复杂的问题划分为多个小问题,也称为状态转移;

小事化了

小问题的解决通常是通过初始化,直接计算结果得到;

具体的步骤

1、将大问题分解为子问题

2、确定状态表示

3、确定状态转移

4、考虑初始状态和边界情况

四、另一个经典的例子——数塔

有如图所示的数塔,要求从顶层走到底层,若每一步只能走到相邻的结点,则经过的结点的数字之和最大是多少?

这里写图片描述

解决思路

1、大事化小。要到达第i层,先要到达第i-1层。并且第i层的第j个节点,只能由i-1层的第j个和第j-1个节点到达。

我们用dp[i][j]表示,走到第i层第j个位置的数字最大和。

那么有dp[i][j]=max(dp[i-1][j], dp[i-1][j-1]) + a[i][j];

2、小事化了。第1层的第1个节点,初始值为dp[1][1]=a[1][1]。(a[x][y]表示第x层,第y个的值)

五、数塔例子的变形——收集苹果

平面上有N*M个格子,每个格子中放着一定数量的苹果。

你从左上角的格子开始,每一步只能向下走或是向右走,每次走到一个格子上就把格子里的苹果收集起来。这样下去,你最多能收集到多少个苹果。

解决思路

1、只能向右走或者向下走,要到达第i行第j列的格子的时候,可以由第i-1行第j列或者第i行第j-1列到达,我们用dp[i][j]表示,走到第i行第j列的最多苹果数,那么有:

dp[i][j]=max(dp[i-1][j], dp[i][j-1]) + a[i][j];

2、第1行第1列,初始值为dp[1][1]=a[1][1],注意事项是边界条件的处理。

六、动态规划经典——01背包问题

给定n件物品和一个容量为m的背包,每件物品都会消耗背包的一定容积c[i],并带来一定价值v[i],要求如何选取装入背包中的物品,使得背包内的物品价值最大。

解决思路

把n件物品放入背包,可以分解为“将前i件物品放入容量为m的背包中”问题。

若只考虑第i件物品的选择,那么问题可以分为两种情况:

1、如果不放第i件物品,问题就转化为“前i-1件物品放入容量为v的背包中”;

2、如果放第i件物品,问题就转化为“前i-1件物品放入剩下的容量为m-c[i]的背包中”;

我们用f[i][j]表示前i个物品,放入容量为j的背包的最大价值,上面的两种情况可以表示为

f[i][j] = max(f[i-1][j], f[i-1][j-c[i]]+v[i]);

初始化条件memset(dp, 0, sizeof(dp));和dp[1][c[1]]=v[1]。

最后遍历f[n][1~m]可以得到最大值。

总结

如果还不能完全理解01背包,那么还需要再仔细理解最优子结构、状态表示和状态转移。

算法能扩展思考方向,完善思维能力。学会“上台阶”、“数塔”、“01背包”这三个题目,能解决算法面试的动态规划部分。

参考及引用

程序员算法基础——动态规划

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

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

相关文章

FFmpeg源代码简单分析-通用-结构体分析-AVCodec

参考链接 FFMPEG结构体分析:AVCodec_雷霄骅的博客-CSDN博客_avcodec AVCodec AVCodec是存储编解码器信息的结构体结构体的定义位于avcodec.h文件中最主要的几个变量 const char *name:编解码器的名字,比较短const char *long_name&#xff…

SLF4J简介与使用(整合log4j)

SLF4J简介与使用(整合log4j) 一、概念 SLF4J的全称是Simple Logging Facade for Java,即简单日志门面。SLF4J并不是具体的日志框架,而是作为一个简单门面服务于各类日志框架,如java.util.logging, logback和log4j。 SLF4J提供了统一的记录…

multism中ui和uo应该怎么表示_王者荣耀:梦泪直播时谈到体验服大改动,表示装备的改动很关键...

王者荣耀的主播梦泪,大家都很熟了,也是一个很强的主播,他对于王者荣耀的理解,还是非常深刻的,而最近王者荣耀的体验服,进行了大改动,也是改变了很多的东西。对此,网友们也是非常的在…

怎么关闭或者卸载ivanti_电脑软件卸载不了怎么办,教您解决电脑软件无法卸载方法技巧...

我们在使用电脑的过程中,肯定会安装各种软件,但是一些软件在使用完之后就不会再使用了,但又无法卸载。下面由小编分享一下电脑安装的软件无法卸载解决方法,如果你在某卸载软件的时候出现无法卸载的情况,不妨通过以下方…

解决Github图片加载失败

问题描述 浏览自己Github某仓库的README.md内时,发现文档的图片始终加载不出,打开浏览器后台,冒出一片红,Failed to load resource: net::ERR_CONNECTION_RESET,如下图所示: 问题分析 可能造成这问题的原…

FFmpeg源代码简单分析-通用-结构体分析-关键结构体之间的关系

参考链接 FFMPEG中最关键的结构体之间的关系_雷霄骅的博客-CSDN博客_ffmpeg 结构体关系 最关键的结构体可以分成以下几类: 解协议(http,rtsp,rtmp,mms) AVIOContext,URLProtocol,URLContext主要存储视音频使用的协…

用Python下载文件

前提条件 需要事先安装requests模块: pip install requests 放码过来 import requestsurl XXX #文件下载来源URL filename #下载到本地后新文件名 r requests.get(url) with open(filename, "wb") as code:code.write(r.content)实战演习 从目标…

FFmpeg源代码简单分析-通用-常见结构体的初始化和销毁(AVFormatContext,AVFrame等)

参考链接 FFmpeg源代码简单分析:常见结构体的初始化和销毁(AVFormatContext,AVFrame等)_雷霄骅的博客-CSDN博客 结构体 AVFormatContext:统领全局的基本结构体。主要用于处理封装格式(FLV/MKV/RMVB等&…

FFmpeg源代码简单分析-通用-avio_open2()

参考链接 FFmpeg源代码简单分析:avio_open2()_雷霄骅的博客-CSDN博客_avio_open avio_open2() 该函数用于打开FFmpeg的输入输出文件avio_open2()的声明位于libavformat\avio.h文件中,如下所示。 /*** Create and initialize a AVIOContext for accessi…

用Tomcat构建一个简单图片服务器

前提条件 Tomcat 7.0.90 方法一&#xff1a;修改配置文件 在TOMCAT_HOME/conf/server.xml配置文件内的<Host>内添加一子标签&#xff1a; <Context docBase"C:\exambase\" path"/img"/>方法二&#xff1a;添加Servlet 新建一应用&#xf…

FFmpeg源代码简单分析-通用-av_find_decoder()和av_find_encoder()

参考链接 FFmpeg源代码简单分析&#xff1a;av_find_decoder()和av_find_encoder()_雷霄骅的博客-CSDN博客_avcodec_find_encoder avcodec_find_encoder avcodec_find_encoder()用于查找FFmpeg的编码器avcodec_find_encoder()的声明位于libavcodec\codec.h 版本差异avcode…

post方法就反回了一个string字符串前台怎么接_Golang Web入门(2):如何实现一个RESTful风格的路由...

摘要在上一篇文章中&#xff0c;我们聊了聊在Golang中怎么实现一个Http服务器。但是在最后我们可以发现&#xff0c;固然DefaultServeMux可以做路由分发的功能&#xff0c;但是他的功能同样是不完善的。由DefaultServeMux做路由分发&#xff0c;是不能实现RESTful风格的API的&a…

FFmpeg源代码简单分析-通用-avcodec_open2()

参考链接 FFmpeg源代码简单分析&#xff1a;avcodec_open2()_雷霄骅的博客-CSDN博客 avcodec_open2() 该函数用于初始化一个音视频编解码器的AVCodecContextavcodec_open2()的声明位于libavcodec\avcodec.h&#xff0c;如下所示。 /*** Initialize the AVCodecContext to use…

统计MySQL中某数据库硬盘占用量大小

放码过来 select TABLE_NAME, concat(truncate(data_length/1024/1024,2), MB) as data_size, concat(truncate(index_length/1024/1024,2), MB) as index_size from information_schema.tables where TABLE_SCHEMA your_db_name order by data_length desc;运行结果 参考…

FFmpeg源代码简单分析-解码-打开媒体的函数avformat_open_input

参考链接 图解FFMPEG打开媒体的函数avformat_open_input_雷霄骅的博客-CSDN博客_avformat_open_input 使用FFmpeg源代码简单分析&#xff1a;avformat_open_input()_雷霄骅的博客-CSDN博客_avformat_open_input() avformat_open_input FFmpeg打开媒体的的过程开始于avformat_…

redis session java获取attribute_面试题:给我说说你能想到几种分布式session实现?...

作者&#xff1a;yanglbme 来源&#xff1a;https://github.com/doocs/advanced-java/blob/master/docs/distributed-system/distributed-session.md# 面试官心理分析面试官问了你一堆 dubbo 是怎么玩儿的&#xff0c;你会玩儿 dubbo 就可以把单块系统弄成分布式系统&#xff0…

FFmpeg源代码简单分析-解码-avformat_find_stream_info()

参考链接 FFmpeg源代码简单分析&#xff1a;avformat_find_stream_info()_雷霄骅的博客-CSDN博客_avformat_find_stream_info avformat_find_stream_info() ​该函数可以读取一部分视音频数据并且获得一些相关的信息avformat_find_stream_info()的声明位于libavformat\avform…

Tail Recursion尾递归

什么是尾递归 Tail Recursion /teɪl rɪˈkɜːrʒn/ In traditional recursion, the typical model is that you perform your recursive calls first, and then you take the return value of the recursive call and calculate the result. In this manner, you don’t g…

FFmpeg源代码简单分析-解码-av_read_frame()

参考链接 ffmpeg 源代码简单分析 &#xff1a; av_read_frame()_雷霄骅的博客-CSDN博客_ffmpeg frame av_read_frame() ffmpeg中的av_read_frame()的作用是读取码流中的音频若干帧或者视频一帧。例如&#xff0c;解码视频的时候&#xff0c;每解码一个视频帧&#xff0c;需要…

FFmpeg源代码简单分析-解码-avformat_close_input()

参考链接 FFmpeg源代码简单分析&#xff1a;avformat_close_input()_雷霄骅的博客-CSDN博客_avformat_close_input avformat_close_input() 本文简单分析FFmpeg的avformat_close_input()函数。该函数用于关闭一个AVFormatContext&#xff0c;一般情况下是和avformat_open_inp…