【C++动态规划】1547. 切棍子的最小成本|2116

【C++动态规划】1547. 切棍子的最小成本|2116

本文涉及知识点

C++动态规划

LeetCode1547. 切棍子的最小成本

有一根长度为 n 个单位的木棍,棍上从 0 到 n 标记了若干位置。例如,长度为 6 的棍子可以标记如下:

在这里插入图片描述

给你一个整数数组 cuts ,其中 cuts[i] 表示你需要将棍子切开的位置。
你可以按顺序完成切割,也可以根据需要更改切割的顺序。
每次切割的成本都是当前要切割的棍子的长度,切棍子的总成本是历次切割成本的总和。对棍子进行切割将会把一根木棍分成两根较小的木棍(这两根木棍的长度和就是切割前木棍的长度)。请参阅第一个示例以获得更直观的解释。
返回切棍子的 最小总成本 。
示例 1:

在这里插入图片描述

输入:n = 7, cuts = [1,3,4,5]
输出:16
解释:按 [1, 3, 4, 5] 的顺序切割的情况如下所示:

在这里插入图片描述

第一次切割长度为 7 的棍子,成本为 7 。第二次切割长度为 6 的棍子(即第一次切割得到的第二根棍子),第三次切割为长度 4 的棍子,最后切割长度为 3 的棍子。总成本为 7 + 6 + 4 + 3 = 20 。
而将切割顺序重新排列为 [3, 5, 1, 4] 后,总成本 = 16(如示例图中 7 + 4 + 3 + 2 = 16)。
示例 2:

输入:n = 9, cuts = [5,6,1,4,2]
输出:22
解释:如果按给定的顺序切割,则总成本为 25 。总成本 <= 25 的切割顺序很多,例如,[4, 6, 5, 2, 1] 的总成本 = 22,是所有可能方案中成本最小的。

提示:

2 <= n <= 106
1 <= cuts.length <= min(n - 1, 100)
1 <= cuts[i] <= n - 1
cuts 数组中的所有整数都 互不相同

动态规划

将0和n加到cuts中,并排序。m = cuts.size

动态规划的状态表示

dp[i][j] 表示切割端点分别为costs[i],costs[j]的木棍,切割完的最小成本。空间复杂度:O(mm)

动态规划的填表顺序

len = j-i
len = 2 to m

动态规划的转移方程

for(int k = i+1; k < j ;i++)
MinSelf(dp[i][j] ,cost[j]-cost[i]+dp[i][k]+dp[i][j])
单个状态转移时间复杂度:O(m),总时间复杂度:O(mmm)

动态规划的初始化

dp[i][i+1] = 0,其它全部是 INT_MAX/2。

动态规划的返回值

dp[0].back()

代码

核心代码

classSolution{public:intminCost(int n, vector<int>& cuts){ cuts.emplace_back(0); cuts.emplace_back(n);sort(cuts.begin(), cuts.end());constint m = cuts.size(); vector<vector<int>>dp(m,vector<int>(m, INT_MAX /2));for(int i =0; i+1< m; i++){ dp[i][i +1]=0;}int j =0;for(int len =2; len <= m; len++){for(int i =0;(j = i + len -1)< m; i++){for(int k = i +1; k < j; k++){ dp[i][j]=min(dp[i][j], cuts[j]- cuts[i]+ dp[i][k]+ dp[k][j]);}}}return dp[0].back();}};

单元测试

int n; vector<int> cuts;TEST_METHOD(TestMethod11){ n =7, cuts ={1,3,4,5};auto res =Solution().minCost(n, cuts);AssertEx(16, res);}TEST_METHOD(TestMethod12){ n =9, cuts ={5,6,1,4,2};auto res =Solution().minCost(n, cuts);AssertEx(22, res);}

扩展阅读

我想对大家说的话
工作中遇到的问题,可以按类别查阅鄙人的算法文章,请点击《算法与数据汇总》。
学习算法:按章节学习《喜缺全书算法册》,大量的题目和测试用例,打包下载。重视操作
有效学习:明确的目标 及时的反馈 拉伸区(难度合适) 专注
闻缺陷则喜(喜缺)是一个美好的愿望,早发现问题,早修改问题,给老板节约钱。
子墨子言之:事无终始,无务多业。也就是我们常说的专业的人做专业的事。
如果程序是一条龙,那算法就是他的是睛
失败+反思=成功 成功+反思=成功

视频课程

先学简单的课程,请移步ZEEKLOG学院,听白银讲师(也就是鄙人)的讲解。
https://edu.ZEEKLOG.net/course/detail/38771
如何你想快速形成战斗了,为老板分忧,请学习C#入职培训、C++入职培训等课程
https://edu.ZEEKLOG.net/lecturer/6176

测试环境

操作系统:win7 开发环境: VS2019 C++17
或者 操作系统:win10 开发环境: VS2022 C++17
如无特殊说明,本算法用**C++**实现。

Read more

初学二叉搜索树踩坑多?C++ 从原理到代码,搞定增删查全流程

初学二叉搜索树踩坑多?C++ 从原理到代码,搞定增删查全流程

🎬 个人主页:Vect个人主页 🎬 GitHub:Vect的代码仓库 🔥 个人专栏: 《数据结构与算法》《C++学习之旅》《计算机基础》 ⛺️Per aspera ad astra. 文章目录 * 1. 二叉搜索树相关概念 * 2. 二叉搜索树的操作 * 2.1. 查找节点 * 2.2. 插入节点 * 2.3. 删除节点 * 3. 二叉搜索树的实现 * 4. 二叉搜索树的应用 * 4.1. K模型 * 4.2. KV模型 1. 二叉搜索树相关概念 如下图所示,二叉搜索树(binary search tree)满足下列条件: 1. 对于根节点,左子树中所有节点的值<根节点的值&

By Ne0inhk
【 C++ 入门】Cyber骇客的 流式文本序列处理器 —— 【 string 类】万字大文带你从0学好C++的string类!

【 C++ 入门】Cyber骇客的 流式文本序列处理器 —— 【 string 类】万字大文带你从0学好C++的string类!

⚡ CYBER_PROFILE ⚡ /// SYSTEM READY /// [WARNING]: DETECTING HIGH ENERGY 🌊 🌉 🌊 心手合一 · 水到渠成 >>> ACCESS TERMINAL <<<[ 🦾 作者主页 ][ 🔥 C语言核心 ][ 💾 编程百度 ][ 📡 代码仓库 ] --------------------------------------- Running Process: 100% | Latency: 0ms 索引与导读 * 一、为什么学习 string类 ? * 二、C++ 标准库中的 string 类 * 2.1)auto和范围for * 2.2)string类的常用接口 * 🚩1)string类的常用构造 * 🚩2)string类对象的容量操作 * ❗注意事项 * 1)size(

By Ne0inhk
Jsp技术入门指南【十四】实现基于MySQL+JDBC+JSP数据库验证的登录界面与登录跳转功能

Jsp技术入门指南【十四】实现基于MySQL+JDBC+JSP数据库验证的登录界面与登录跳转功能

Jsp技术入门指南【十四】实现基于MySQL+JDBC+JSP数据库验证的登录界面与登录跳转功能 * 前言 * 第一步:加入驱动包与Maven * 第二步、创建并导入web库 * 第三步、连接本地数据库的java代码 * 核心代码讲解 * 第四步、创建数据库 * 第五步、导入并修改JSP登录文件 前言 * 在之前的博客中,我们详细探讨了 JSTL 中 SQL 标签库和自定义标签库的基础用法,并展示了如何利用这些标签库实现 MySQL 数据库连接以及数据分页展示功能。 * 本文将继续深入,介绍如何基于 MySQL 数据库实现用户登录验证功能,包括登录界面设计、用户身份验证以及登录成功 / 失败后的页面跳转处理。 我的个人主页,欢迎来阅读我的其他文章 https://blog.ZEEKLOG.net/2402_83322742?spm=1011.2415.3001.5343 我的JSP知识文章专栏 欢迎来阅读指出不足 https:

By Ne0inhk
【C++】第二十五节—C++11 (上) | 详解列表初始化+右值引用和移动语义

【C++】第二十五节—C++11 (上) | 详解列表初始化+右值引用和移动语义

嗨,好久不见,我是云边有个稻草人,偶尔中二的C++领域博主与你分享专业知识^(* ̄(oo) ̄)^ 《C++》本篇文章所属专栏—持续更新中—欢迎订阅~ 最近的富文本编辑器给我整不会了,ε=(´-`*)))唉,多了横虚线,点某个位置老是会跳到别的位置或者出现了选中文字或图片的情况 目录 一、C++11的发展历史 二、列表初始化 1. C++98传统的{ } 2. C++11中的{} 3. C++11中的std::initializer_list 三、右值引用和移动语义(重点) 1. 左值和右值 2. 左值引用和右值引用 3. 引用延长生命周期 4. 左值和右值的参数匹配 5. 右值引用和移动语义的使用场景 (1)左值引用主要使用场景回顾 (2)移动构造和移动赋值

By Ne0inhk