动态规划(有背包问题)

动态规划——分组背包问题 聪明人都会点进来学习!!动态规划看这一篇就够了!!!本文详细讲解了动态规划的核心思路(配有图片),还以经典问题——分组背包问题为例,先从基础解法开始讲解思路,再一步步优化,带有完整代码(有详细注释),对于难以理解的地方还会举例讲解,还会和01背包问题对比思考,赶紧点进来学习吧!!! 阅读详情

目录

1.动态规划的介绍

2.动态规划的例题

第1道题 数字三角形

(如果想看递归写法可以到我的记忆化递归里去看看记忆化递归_将递归程序记忆化-优快云博客)

第2道题最长公共子序列(模板) 

第3道题 最长上升子序列

第4道题最大子段和

背包系列问题

01背包

完全背包


1.动态规划的介绍

是解决多阶段决策问题常用的最优化理论,该理论由美国数学家Bellman等人在1957年提出,用于研究多阶段决策过程的优化问题。


动态规划方法的原理就是把多阶段决策过程转化为一系列的单阶段决策问题,利用各个阶段之间的递推关系,逐个确定每个阶段的最优化决策,最终堆看出多阶段决策的最优化决策结果。


动态规划适合求解多阶段(状态转换)决策问题的最优解,决策的阶段可以随时间划分也可以随着问题的演化状态划分。问题都具有的一个性质就是“最优子结构”。

而动态规划的重点就是在于找出状态转移方程。

接下来我们看几道例题

2.动态规划的例题

第1道题 数字三角形

(如果想看递归写法可以到我的记忆化递归里去看看记忆化递归_将递归程序记忆化-优快云博客)

数字三角形的洛谷链接:[USACO1.5] [IOI1994]数字三角形 Number Triangles - 洛谷

这道题问的就是怎样走可以数字和最大(一棵树);

这道题思路很简单,我们可以从这棵树的底部开始进行运算,比大小。

所以我们的动态转移方程就是:d[i][j] = a[i][j]+max(d[i+1][j],d[i+1][j+1]);//它等于它底下的节点中的最大值加上本身

最后代码:

#include <bits/stdc++.h>
using namespace std;
int d[1005][1005];
int a[1005][1005];
int n;
int main(){
    cin >> n;
    for (int i =1; i <= n+1; i++){
        for (int j =1; j <= i; j++){
            cin >> a[i][j];
        }
    }
    for (int j =1; j <= n; j++){
        d[n][j] = a[n][j];
    }
    for (int i =n-1; i >= 1; i--){
        for (int j =1; j <= i; j++){
            d[i][j] = a[i][j]+max(d[i+1][j],d[i+1][j+1]);
        }
    }
    cout << d[1][1];
    return 0;
}

第2道题最长公共子序列(模板) 

注意子序列是不连续的(也可以连续,但不强求连续)

这道题思路并不是那么难;, A、B,2个字符串每一号位进行比较,如果它们这两个字符相等的话,我们就要让dp[i][j]=dp[i-1][j-1]+1,其中+1代表增加了一个公共子序列中的字符,然后再加上没有它们两个字符的时候的值。如果这两个字符不相等,那就取不包含第一个字符和不包含第二个字符的最长子序列最大值(长度)。

所以我们可以得出的状态转移公式:

if (a[i-1] == b[j-1]){
	dp[i][j] = dp[i-1][j-1]+1;         
}
else{
	dp[i][j] = max(dp[i][j-1],dp[i-1][j]);
}

总体代码:

#include <bits/stdc++.h>
using namespace std;
int dp[1005][1005];
int main(){
    int n ,m;
    cin >> n >> m;
    string a,b;
    cin >> a >> b;
    for (int i = 1; i <= n; i++){
        for (int j = 1; j <= m; j++){
            if (a[i-1] == b[j-1]){
				dp[i][j] = dp[i-1][j-1]+1;
                
            }
            else{
				dp[i][j] = max(dp[i][j-1],dp[i-1][j]);
               
            }
        }
    }
    cout << dp[n][m];
    return 0;
}

第3道题 最长上升子序列

 最长上升子序列 - 洛谷

上面是洛谷的链接⬆️

这道题的总体思路:

dp[i]的意思是从0号位到i号位最长上升子序列(子序列的结尾是i号位)

进行循环构建出DP数组

状态转移公式:


            if (a[j] < a[i]){
                dp[i] = max(dp[i],dp[j]+1);
            }

最后再用M算出整个数组中的最大值.

最后代码:

#include <bits/stdc++.h>
using namespace std;
int dp[50000];
int a[100000];
int main(){
	int n; 
    cin >> n;
    for (int i = 0; i <n; i++){
        cin >> a[i];
    }
    int m = 0;
    for (int i = 0; i <n; i++){
        dp[i] = 1;
        for (int j = 0; j <i; j++){
            if (a[j] < a[i]){
                dp[i] = max(dp[i],dp[j]+1);
            }
        }
        if (dp[i] > m){
            m = dp[i];
        }
    }
    cout << m;
    return 0;
}

第4道题最大子段和

( ̄y▽ ̄)╭最大子段和 - 洛谷

这道题的思路很简单,dp[i]代表着从0号位到第i号位结尾为第i号位的最大子段和是多少

那就可以分为(取前面的和)和(不取前面的和)

在求一个最大值中的最大值就OK了

状态转移公式:


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

总体代码:

#include <bits/stdc++.h>
using namespace std;
long long dp[500005];
long long a[500000];
int main(){
	int n; 
    cin >> n;
    for (int i = 0; i <n; i++){
        cin >> a[i];
    }
    long long m = -2e9;
    for (int i = 0; i <n; i++){
        dp[i] = max(dp[i-1]+a[i],a[i]);
        m = max(m,dp[i]);
    }
    
    cout << m;
    return 0;
}

背包系列问题

01背包

0< N,M ≤1000

0< vi,pi ≤1000

我们可以分成几种情况

 dp[i][j]代表了1~i个东西和可装重量为j的书包

dp[i-1][j-v[i]]代表了如果总重量加入了我们第i个物品(也就是放了),最终可以得到多少价值的东西.

转移公式:

if (j < v[i]){
    dp[i][j] = dp[i-1][j];
}
else{
    dp[i][j] = max(dp[i-1][j],dp[i-1][j-v[i]]+w[i]);
}

最后代码:

#include <bits/stdc++.h>
using namespace std;
int dp[1005][1005];
int main(){
    int n,m;
    cin >> n >> m;
    int v[1005],w[1005];
    for (int i = 1; i <= n; i++){
        cin >> v[i] >> w[i];
    }
    for (int i = 1; i <= n; i++){
        for (int j = 1; j <= m; j++){
            if (j < v[i]){
                dp[i][j] = dp[i-1][j];
            }
            else{
                dp[i][j] = max(dp[i-1][j],dp[i-1][j-v[i]]+w[i]);
            }
        }
    }
    cout << dp[n][m];
    return 0;
}

完全背包

疯狂的采药:疯狂的采药 - 洛谷

完全背包和01背包的不同在于一个东西它可以有无限个,也就是说你可以取无限次,只要你背包还有容量那我们就要把i-1改成i因为这一个东西它可以取很多次.

在这里我们用的是一维数组,我们要倒过来循环

转移方程:(只不过这里的写法不同,和上面的判断条件意思是一样的)


            dp[j]= dp[j];
            if (j >= w[i]){
                dp[j] = max(dp[j],dp[j-w[i]]+c[i]);
            }

 所有代码:

#include <bits/stdc++.h>
using namespace std;
long long w[10000005],c[10000005];
long long dp[10000005];
long long m,n;
int main(){
    cin >> m >>n;
    for (long long i = 1; i <= n; i++){
        cin >> w[i] >> c[i];
        for (long long j = 1; j <= m; j++){
            dp[j]= dp[j];
            if (j >= w[i]){
                dp[j] = max(dp[j],dp[j-w[i]]+c[i]);
            }
        }
    }
    
    cout << dp[m];
    return 0;
}

4、基于球面波展开的近场/远场变换技术解析 本文深入解析了基于球面波展开的近场/远场变换技术,涵盖坐标系统选择、截断测量处理、高级SWE方法及实际应用场景。重点介绍了广义SWE、全探头补偿、平移SNF测量(TSWE)等关键技术,结合吸收材料与导电地板系统的误差处理方案,系统总结了各类方法的优缺点与适用场景,并通过流程图和案例分析展示了技术应用路径。该技术在汽车、通信和航空航天领域的天线测量中具有重要价值,可显著提升测量效率与精度。 阅读详情

相关推荐

LTSPICE使用教程:入门指导

LTSPICE仿真工具入门指导

焊武大帝的专栏 5万+

运筹系列87:julia求解随机动态规划问题入门

看一个简单的数值优化的例子:我们将其建立为一个N阶段的问题:初始值为M。结果为非常接近理论最优值。

kittyzc的博客 1941

MOSFET开关损耗全面讲解:从原理到优化策略

深入剖析MOSFET开关损耗的产生机制,结合实际应用场景,讲解如何通过驱动设计和电路优化降低损耗,提升系统效率。重点关注mosfet在高频开关下的表现与热管理。

weixin_29476595的博客 1061

随机过程之基本概念(一)

随着对课题的深入接触,越来越感觉到概率论与数理统计对于科学和工程的重要意义,之前确实小看了。尤其是”随机过程“,作为数理统计的重要部分,应用包罗万象,例如:气象预报、通信工程、金融工程、人口理论和可靠性与质量控制等各个方面。下面简单介绍下随机过程的基本概念。   1.发展背景 随机过程的早期研究可追溯到玻尔兹曼等人在统计力学中的研究中;Erlang等在电话流中研究了Possion过程;而整个...

王子云的博客 3万+

PhotoShop人像精修必备:Portraiture插件安装与破解全攻略(附最新下载)

本文深度解析了Portraiture插件在PhotoShop人像精修中的核心价值与应用。它不仅是智能磨皮工具,更集成了自适应平滑、肤色蒙版与细节增强等功能,能精准处理皮肤瑕疵并保留质感。文章重点分享了其合法安装方法、无缝融入ACR到PS的专业工作流,以及针对不同肤质的高级调整技巧,旨在帮助用户构建高效、无损的人像精修流程。

terraform7cloud的博客 380

保姆级教程:手把手调试PX4Ctrl的油门映射与姿态控制(附ROS节点配置)

本文提供PX4Ctrl的深度调参指南,涵盖油门映射、姿态控制及ROS节点配置等关键环节。通过详细解析PX4控制器的核心逻辑、递归最小二乘法(RLS)参数估计及状态机设计,帮助开发者优化无人机飞控性能。附实战案例与安全调试建议,适合PX4开发者进阶学习。

weixin_30363981的博客 382

牛客_随机过程_动态规划

前言 这是一道随机游走的问题,应归属随机过程。这道题求期望,无非考虑左右游走两种情况,巧妙的是,递归等式的右端会重复出现左端项。 #include<bits/stdc++.h> using namespace std; double p[100100], dp[100100]; int main() { int n; cin >> n; for(int i = 0; i < n; i++) cin >> p[i]; dp

小楼一夜听春雨 510

Ethercat学习-从站源码生成

移植平台GD32F450,从站芯片AX58100

西澳峰的博客 9226

动态规划——01背包问题

面向小白的动态规划之01背包问题的详细讲解

Wu_L7的博客 3万+

AD9361功能介绍和使用

AD9361使用分数分频锁相环(PLL)来产生发射机和接收机本地振荡器(LO)频率和BB PLL。BB PLL 可用于数据转换、数字滤波器和 |/O 端口。PLL的参考时钟可以由外部振荡器或外部晶体(XO)和数字可编程片内可变电容提供,电容微调产生参考时钟频率,XO和微调电容的组合统称为DCXO。有多个天线输入的分集系统。接收链数据首先经过低噪声放大器(LNA),然后是同相(1)和正交(Q)放大器,混频器和频带整形滤波器,可将接收到的信号下变频为基带以进行数字化。时分双工(TDD)和频分双工(FDD)。。。

wangjie36的博客 1万+

学 Simulink——基于载波移相的级联 H 桥双向 DC-AC 逆变器仿真

本文手把手教程基于载波移相(CPS-SPWM)的三相级联H桥双向DC-AC逆变器仿真,通过Simulink实现N=3(七电平)、每模块200V直流源、1kHz开关频率的系统建模。核心在于载波相位错开60°,使谐波集中于6kHz边带,等效开关频率达6kHz,显著降低器件损耗与输出纹波。结合并网电流双闭环(dq解耦)、功率/电压/SoC均衡控制及死区补偿,验证了THD<2%、有功跟踪误差<5%、直流电压与SoC均衡收敛至±3%和2%以内。工程上适用于高压储能系统,具备模块化、故障容错与高电能质量优势

MHD0815的博客 261

【动态规划】01背包问题

【动态规划】01背包问题

一个专注于客户端开发的技术er,不定期更新Android,Flutter,HormonyOS等方向的使用心得和感悟 6843

基于上下文的 Listwise 重排模型(一):miRNN

2018年阿里团队提出的miRNN(Mutual Influence aware RNN)模型,首次将电商搜索重排建模为全局优化问题,通过RNN捕捉商品序列的相互影响,结合Beam Search生成最优排序,在淘宝搜索中实现GMV(商品交易总额)提升5%的突破。本文将结合论文细节与通俗案例,拆解这一工业级重排框架的核心逻辑。

进一步有进一步的欢喜~ 1918

动态规划之背包问题

0-1背包问题;完全背包问题;多重背包问题;动态规划;

rain_lin2000的博客 1520

WINCC7.3破解文件

WINCC7.3硬件够破解文件,有需要的下载!WINCC7.3硬件够破解文件,有需要的下载!

ET2012新版免狗免安装绿色软件

ET2012新版免狗免安祖昂绿色软件。,新界面,新视觉,

动态规划之背包问题(C语言)

动态规划 动态规划(英语:Dynamic programming,简称DP)是一种通过把原问题分解为相对简单的子问题的方式求解复杂问题的方法。 动态规划常常适用于有重叠子问题和最优子结构性质的问题 动态规划思想大致上为:若要解一个给定问题,我们需要解其不同部分(即子问题),再合并子问题的解以得出原问题的解。 由于通常许多子问题非常相似,为此动态规划法试图仅仅解决每个子问题一次,从而减少计算

一串代码的博客 1万+

计算机控制技术及应用

《计算机控制技术及应用》通过总结作者的科研成果和吸收国内外的先进理论、方法和技术,以计算机控制系统的网络化、开放化、智能化和集成化发展趋势为主线索,主要介绍计算机控制系统的基本概念和计算机控制系统的典型形式,计算机控制系统的数学描述与基本分析方法,以及数字PID控制器、最少拍控制系统、达林算法、状态变量设计法等设计方法及其各种改进算法。重点突出计算机控制系统输入输出通道接口的设计方法和典型控制系统的设计案例与实现方法等。

动态规划 背包问题

③确定转移方程:由于a[i][j]表示前i个物品中,容量为j时能够放下的最大价值,所以,如果不能够放入第i个物品,那么直接f[i,j]=f[i-1,j]即可,如果能够放下第i个物品(即j向右扫),我们只需要选择不放入第i个物品和放入第i个物品(值为恰好去掉第i个物品时的最大值+第i个物品的值)的最大值即可。一共有N个物品,有一个容量为M的背包,这N个物品,分别占用Vi的容量和具有Pi的价值,要求组合出不超过背包容量的物品,使其价值最大。子问题:从前i个物品中选,放在体积为i的背包中,总价值最大。

m0_63415841的博客 1193

STM32F407中文手册

STM32f407中文手册 本参考手册面向应用开发人员,提供有关使用 STM32F405xx/07xx、STM32F415xx/17xx、 STM32F42xxx 和 STM32F43xxx 微控制器存储器与外设的完整信息。STM32F405xx/07xx、STM32F415xx/17xx、STM32F42xxx 和 STM32F43xxx 构成一个微 控制器系列,各产品具有不同的存储器大小、封装和外设。有关订购信息以及器件的机械与电气特性,请参见数据手册。有关 ARM Cortex™-M4F 内核的信息,请参见《Cortex™-M4F 技术参考手册》。

动态规划算法解决背包问题

什么是动态规划算法 1)动态规划(Dynamic Programming)算法的核心思想是:将大问题划分为小问题进行解决,从而一步步获取最优解的处理算法 2)动态规划算法与分治算法类似,其基本思想也是将待求解问题分解成若干个子问题,先求解子问题,然后从这些子问题的解得到原问题的解。 3)与分治法不同的是,适合于用动态规划求解的问题,经分解得到子问题往往不是互相独立的。 (即下一个子阶段的求解...

interesting_code的博客 4756

c++动态规划解决01背包问题

动态规划主要运用状态转移方程(即递推方程)解决步骤问题,一般来说遍历方向有从前到后和从后到前,具体问题具体分析下面具体讲解一下动态规划的01背包问题:(一般来说,01背包问题不会刻意出题,但是会解决有限的容量中得到利益最大的一类问题)动态规划(Dynamic Programming, DP)动态规划是一种在数学、计算机科学和经济学中使用的,通过把原问题分解为相对简单的子问题的方式求解复杂问题的方法。它通常用于求解最优化问题。

qq_63176310的博客 2707

动态规划——背包问题

#动态规划#01背包问题

2501_90864902的博客 1198

背包问题 动态规划

背包问题核心 优化一般就是优化状态转移方程 01背包问题 有 N 件物品和一个容量是 V 的背包。每件物品只能使用一次。 第 i 件物品的体积是 vi,价值是 wi。 求解将哪些物品装入背包,可使这些物品的总体积不超过背包容量,且总价值最大。 输出最大价值。 输入格式 第一行两个整数,N,V,用空格隔开,分别表示物品数量和背包容积。 接下来有 N 行,每行两个整数 vi,wi,用空格隔开,分别表示第 i 件物品的体积和价值。 输出格式 输出一个整数,表示最大价值。 数据范围 0<N,V≤1000 0

m0_53203911的博客 6432

c++动态规划——背包问题

问题基础:有N件物品和一个容量为C的背包。第i件物品的体积是W[i],价值是V[i]。求解将哪些物品装入背包可使这些物品的重量总和不超过背包容量,且价值总和最大。 怎样才能得到放入书包物品的的最大价值呢? 解决方法——【动态规划】 运筹学的分支,纠结决策过程最优化的数学方法 把多阶段问题分解为相互联系单一阶段小问题求解,上一阶段的决策可以对下一阶段的决策产生影响 各个阶段的决

YinghaoGuo的博客 1万+

动态规划背包问题

文章目录一、动态规划是什么?二、背包问题三、使用动态规划优化一·优化过程一·自我思考(个人想法)总结 一、动态规划是什么? 将问题分为子问题,并先着手解决这些小问题 二、背包问题 背包问题:现在有四件商品,分别为音响3000美元重四磅,笔记本电脑2000美元重三磅,吉他1500美元一磅,iphone2000美元一磅 现在假设你有一个可以装下四磅的物品,在上面提供的物品中如何是装下的物品价值最大,简单的算法就是尝试各种商品组合,并找出价值最高的组合。 但是这样的话时间复杂度为O(2^n),这样的算法是很慢的

m0_52387040的博客 2069

动态规划之背包问题的Python实现

目录 1.问题描述 2.动态规划之网格法 3.python实现 1.问题描述 题目来源于《算法图解》第9章练习题9.2,如下图所示。 对于背包问题,通常的做法有列举法、贪婪算法和动态规划 (1)列举法:列举出所有的可能情况,再选择最优解,但当情况很多时,这种算法复杂度很高 (2)贪婪算法:在容量允许范围内,每次都拿剩余物品中价值最高的,贪婪算法能够快速解决复杂度很高的问题,但...

ha_____ha的博客 1395
上一篇: 反弹球python小游戏
下一篇: C++里的随机数
B757-300
博客等级 码龄4年 259粉丝 52原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值