iis服务器助手广告广告
返回顶部
首页 > 资讯 > 后端开发 > Python >Python之动态规划
  • 392
分享到

Python之动态规划

python动态规划 2023-08-30 14:08:12 392人浏览 独家记忆

Python 官方文档:入门教程 => 点击学习

摘要

序言 最近在学习python语言,语言有通用性,此文记录复习动态规划并练习Python语言。 动态规划(Dynamic Programming) 动态规划是运筹学的一个分支,是求解决策过程最优化的过程。20世纪50年代初,美国数学家贝尔曼(

序言

最近在学习python语言,语言有通用性,此文记录复习动态规划并练习Python语言。

动态规划(Dynamic Programming)

动态规划是运筹学的一个分支,是求解决策过程最优化的过程。20世纪50年代初,美国数学家贝尔曼(R.Bellman)等人在研究多阶段决策过程的优化问题时,提出了著名的最优化原理,从而创立了动态规划。动态规划的应用极其广泛,包括工程技术、经济、工业生产、军事以及自动化控制等领域,并在背包问题、生产经营问题、资金管理问题、资源分配问题、最短路径问题和复杂系统可靠性问题等中取得了显著的效果。

基本思想:将待求解问题分解成若干个子问题,先求解子问题,然后从这些子问题的解得到原问题的解。与分治法不同的是,适合于用动态规划求解的问题,经分解得到子问题往往不是互相独立的。

斐波那契数列(Fibonacci sequence)

斐波那契数列,又称黄金分割数列,因数学家莱昂纳多·斐波那契(Leonardo Fibonacci)以兔子繁殖为例子而引入,故又称“兔子数列”,其数值为:1、1、2、3、5、8、13、21、34……在数学上,这一数列以如下递推的方法定义:F(0)=1,F(1)=1, F(n)=F(n - 1)+F(n - 2)(n ≥ 2,n ∈ N*)。

先以斐波那契数列为例,了解动态规划。

def fibonacci(num):    if num == 0:        return 1    if num == 1:        return 1    return fibonacci(num - 1) + fibonacci(num - 2)if __name__ == "__main__":    print(fibonacci(10))

在这里插入图片描述
上述是以递归的方式实现的,然而递归方式存在以下几个缺点:

  • 1)递归调用,占用空间大;
  • 2)递归太深,容易发生栈溢出;
  • 3)可能存在大量重复计算;
结果(n-1)项(n-2)项
f(n)f(n-1)f(n-2)
f(5)f(4)f(3)
f(4)f(3)f(2)
f(3)f(2)f(1)
f(2)f(1)f(0)

以上述表格为例,可以看到在求下一个递归结果时,计算了之前已经计算出来的结果,存在重复计算项。

如果采用动态规划的方式,那么可以节省计算,采用数组暂存之前已经计算出来的结果。如下,

def fibonacci_dp(num):    # 定义一个数组暂存dp结果,数组初始值为-1    dp = [-1] * (num + 1)    dp[0] = 1    dp[1] = 1    for i in range(2, num + 1):        dp[i] = dp[i - 1] + dp[i - 2]    return dp[num]if __name__ == "__main__":    print(fibonacci_dp(10))

在这里插入图片描述

不同路径

上面的斐波那契数列是一维数组,较为简单,下面以二维数组为例。

题目描述

一个机器人位于一个 m x n 网格的左上角 (起始点在下图中标记为 “Start” )。

机器人每次只能向下或者向右移动一步。机器人试图达到网格的右下角(在下图中标记为 “Finish” )。

问总共有多少条不同的路径?在这里插入图片描述

示例1: 输入:m = 3, n = 7 输出:28

示例2: 输入:m = 3, n = 2 输出:3
解释: 从左上角开始,总共有 3 条路径可以到达右下角。
1.向右 -> 向下 -> 向下
2.向下 -> 向下 -> 向右
3.向下 -> 向右 -> 向下
示例3:
输入:m = 7, n = 3 输出:28
示例4:
输入:m = 3, n = 3 输出:6
1 <= m, n <= 100
题目数据保证答案小于等于 2 * 10^9

python代码

class UniquePaths(object):    def uniquePaths(self, m: int, n: int) -> int:        """        :type m: int        :type n: int        :rtype: int        """        # 初始化一个二维数组        dp = [[0] * n for _ in range(m)]        for i in range(m):            dp[i][0] = 1        for j in range(n):            dp[0][j] = 1        for i in range(1, m):            for j in range(1, n):                dp[i][j] = dp[i - 1][j] + dp[i][j - 1]        return dp[m - 1][n - 1]if __name__ == "__main__":    demo = UniquePaths()    print(demo.uniquePaths(7, 3))

在这里插入图片描述

最小路径和

题目描述

给定一个包含非负整数的 m x n 网格 grid ,请找出一条从左上角到右下角的路径,使得路径上的数字总和为最小。

说明:一个机器人每次只能向下或者向右移动一步。

在这里插入图片描述

示例1:
输入:grid = [[1,3,1],[1,5,1],[4,2,1]]
输出:7
解释:因为路径 1→3→1→1→1 的总和最小。
示例2:
输入:grid = [[1,2,3],[4,5,6]]
输出:12
提示:
m == grid.length
n == grid[i].length
1 <= m, n <= 200
0 <= grid[i][j] <= 100

python代码

class MinPathSum(object):    def minPathSum(self, grid):        """        :type grid: List[List[int]]        :rtype: int        """        row = len(grid)        column = len(grid[0])        # 定义dp[i][j]为到(i,j)处的最小路径和        dp = [[0] * column for _ in range(row)]        dp[0][0] = grid[0][0]        # 第0行j列        for j in range(1, column):            dp[0][j] = dp[0][j - 1] + grid[0][j]        # 第i行0列        for i in range(1, row):            dp[i][0] = dp[i - 1][0] + grid[i][0]        # 非第0行或第0列        for i in range(1, row):            for j in range(1, column):                dp[i][j] = min(dp[i - 1][j], dp[i][j - 1]) + grid[i][j]        return dp[row - 1][column - 1]if __name__ == "__main__":    demo = MinPathSum()    grid = [[1, 3, 1], [1, 5, 1], [4, 2, 1]]    print(demo.minPathSum(grid))

在这里插入图片描述

零钱兑换

题目描述

给你一个整数数组 coins ,表示不同面额的硬币;以及一个整数 amount ,表示总金额。

计算并返回可以凑成总金额所需的 最少的硬币个数 。如果没有任何一种硬币组合能组成总金额,返回 -1 。

你可以认为每种硬币的数量是无限的。

示例 1:
输入:coins = [1, 2, 5], amount = 11
输出:3
解释:11 = 5 + 5 + 1
示例 2:
输入:coins = [2], amount = 3
输出:-1
示例 3:
输入:coins = [1], amount = 0
输出:0
提示:
1 <= coins.length <= 12
1 <= coins[i] <= 231 - 1
0 <= amount <= 104

python代码

class CoinChange(object):    def coinChange(self, coins: list[int], amount: int) -> int:        """        :type coins: List[int]        :type amount: int        :rtype: int        """        # 状态转移方程dp(i) = min(dp(i-Cj)) + 1,Cj为货币面值        """        i<0  忽略        i==0 dp[0] = 0        i==1 dp[1] = min(dp[1-1], dp[1-2], dp[1-5]) + 1 = 1        i==2 dp[2] = min(dp[2-1], dp[2-2], dp[2-5]) + 1 = 1        i==3 dp[3] = min(dp[3-1], dp[3-2], dp[3-5]) + 1 = 2        i==4 dp[4] = min(dp[4-1], dp[4-2], dp[4-5]) + 1 = 2        ... ...        """        dp = [0] * (amount + 1)        dp[0] = 0        for i in range(1, amount + 1):            mini = int(1e9)            for coin in coins:                if i >= coin:                    res = dp[i - coin]                    if 0 <= res < mini:                        mini = res            dp[i] = mini + 1 if mini < int(1e9) else -1        if amount < 1:            return 0        return dp[amount]if __name__ == "__main__":    demo = CoinChange()    coins = [1, 2, 5]    amount = 11    print(demo.coinChange(coins, amount))

在这里插入图片描述

来源地址:https://blog.csdn.net/zkkzpp258/article/details/132549864

--结束END--

本文标题: Python之动态规划

本文链接: https://www.lsjlt.com/news/382973.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

本篇文章演示代码以及资料文档资料下载

下载Word文档到电脑,方便收藏和打印~

下载Word文档
猜你喜欢
  • Python之动态规划
    序言 最近在学习python语言,语言有通用性,此文记录复习动态规划并练习python语言。 动态规划(Dynamic Programming) 动态规划是运筹学的一个分支,是求解决策过程最优化的过程。20世纪50年代初,美国数学家贝尔曼(...
    99+
    2023-08-30
    python 动态规划
  • 动态规划详解Python
    动态规划 动态规划(Dynamic Programming)是一种用于解决复杂问题的算法设计方法。它通常用于优化问题,其中问题可以被分解成一系列重叠子问题,通过存储并重复使用已经解决过的子问题的解,可...
    99+
    2023-09-09
    动态规划 python 代理模式
  • python动态规划算法怎么用
    小编给大家分享一下python动态规划算法怎么用,希望大家阅读完这篇文章之后都有所收获,下面让我们一起去探讨吧!python有哪些常用库python常用的库:1.requesuts;2.scrapy;3.pillow;4.twisted;5...
    99+
    2023-06-14
  • 什么是动态规划
    这篇文章主要介绍“什么是动态规划”,在日常操作中,相信很多人在什么是动态规划问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作方法,希望对大家解答”什么是动态规划”的疑惑有所帮助!接下来,请跟着小编一...
    99+
    2024-04-02
  • 动态规划之什么是多重背包
    本篇内容主要讲解“动态规划之什么是多重背包”,感兴趣的朋友不妨来看看。本文介绍的方法操作简单快捷,实用性强。下面就让小编来带大家学习“动态规划之什么是多重背包”吧!多重背包有N种物品和一个容量为V 的背包。...
    99+
    2024-04-02
  • 60题学会动态规划系列:动态规划算法第三讲
    简单多状态问题 文章目录 一.按摩师二.打家劫舍系列三.删除并获得点数四.粉刷房子 1.按摩师 力扣链接:力扣 一个有名的按摩师会收到源源不断的预约请求,每个预约都可以选择接或不接。在每次预约服务之间要有休息时间,因...
    99+
    2023-10-05
    c++ 后端 算法 动态规划 力扣
  • LeetCode 动态规划之矩阵区域和详情
    目录题目题解解题分析解题代码题目 矩阵区域和 给你一个 m x n 的矩阵 mat 和一个整数 k ,请你返回一个矩阵&n...
    99+
    2024-04-02
  • Java动态规划之如何编辑距离问题
    这篇文章给大家分享的是有关Java动态规划之如何编辑距离问题的内容。小编觉得挺实用的,因此分享给大家做个参考,一起跟随小编过来看看吧。动态规划过程是:每次决策依赖于当前状态,又随即引起状态的转移。一个决策序列就是在变化的状态中产生出来的,所...
    99+
    2023-05-30
    java
  • Python最大连续区间和动态规划
    be前言:期末临近,考Python的同学可以练练 问题描述:给定一段长度为N的整数序列A,请从中选出一段连续的子序列(可以为0)使得这段的总和最大 这里就不提暴力法了,只能在OJ系...
    99+
    2024-04-02
  • C语言动态规划之背包问题详解
    01背包问题        给定n种物品,和一个容量为C的背包,物品i的重量是w[i],其价值为v[i]。问如何选择装入背包的物品,使得装入背...
    99+
    2024-04-02
  • Java动态规划之丑数问题实例讲解
    问题描述: 我们把只包含质因子 2、3 和 5 的数称作丑数(Ugly Number)。求按从小到大的顺序的第 n 个丑数。 注: 1也是丑数 思路: 我们来分析一下丑数如何得到,肯...
    99+
    2024-04-02
  • c++动态规划经典算法
    目录基本思想重要分析问题方法动态规划算法实例1、台阶问题2、从矩阵左上角走到右下角最短路径问题3、最大子数组问题4、最长公共子序列基本思想    &nb...
    99+
    2024-04-02
  • C++编辑距离(动态规划)
    题目描述: 给你两个单词 word1 和 word2,请你计算出将 word1 转换成 word2 所使用的最少操作数 。 我们可以对一个单词进行如下三种操作: 插入一个字符删除一个...
    99+
    2024-04-02
  • java中什么是动态规划
    这篇文章给大家介绍java中什么是动态规划,内容非常详细,感兴趣的小伙伴们可以参考借鉴,希望对大家能有所帮助。java基本数据类型有哪些Java的基本数据类型分为:1、整数类型,用来表示整数的数据类型。2、浮点类型,用来表示小数的数据类型。...
    99+
    2023-06-14
  • C语言深入探究动态规划之区间DP
    目录写在前面石子合并写在前面 之前讲过背包问题,线性DP不知道大家忘了吗,这次是区间DP 石子合并 题意: 合并 N 堆石子,每次只能合并相邻的两堆石子,求最小代价 解题思路: ...
    99+
    2024-04-02
  • C语言深入探究动态规划之线性DP
    目录写在前面数字三角形最长上升子序列最长上升子序列 II最长公共子序列写在前面 之前讲过背包问题,不知道大家忘了吗,如果忘了可以点这里,这次是线性DP 数字三角形 状态表示:f[i...
    99+
    2024-04-02
  • python实现动态规划算法的示例代码
    动态规划(Dynamic Programming,DP)是一种常用的算法思想,通常用于解决具有重叠子问题和最优子结构性质的问题。动态规划算法通常是将问题分解为子问题,先解决子问题,再...
    99+
    2023-02-16
    python 动态规划算法
  • 暴力递归转动态规划(二)
    上一篇已经简单的介绍了暴力递归如何转动态规划,如果在暴力递归的过程中发现子过程中有重复解的情况,则证明这个暴力递归可以转化成动态规划。 这篇帖子会继续暴力递归转化动态规划的练习,这道题有点难度。 题目 给定一个整型数组arr[],代表数值不...
    99+
    2023-08-30
    动态规划 算法 java 暴力递归
  • Java动态规划之硬币找零问题实现代码
    动态规划的基本思想是将待求解问题分解成若干个子问题,先求解子问题,并将这些子问题的解保存起来,如果以后在求解较大子问题的时候需要用到这些子问题的解,就可以直接取出这些已经计算过的解而免去重复运算。保存子问题的解可以使用填表方式,例如保存在数...
    99+
    2023-05-30
    java 算法 硬币找零
  • 如何实现动态规划进阶
    本篇内容介绍了“如何实现动态规划进阶”的有关知识,在实际案例的操作过程中,不少人都会遇到这样的困境,接下来就让小编带领大家学习一下如何处理这些情况吧!希望大家仔细阅读,能够学有所成!案例 1问:给定一个包含非负整数的 m x n 网格,请找...
    99+
    2023-06-15
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作