当前位置: 首页 > news >正文

算法刷题记录-DP(LeetCode)

746. Min Cost Climbing Stairs

代码

    int minCostClimbingStairs(vector<int>& cost) {if (cost.size()<2){return 0;}int cache[cost.size()+1];cache[0]=0;cache[1]=0;for (int i = 2; i <= cost.size(); ++i) {cache[i]= min(cache[i-2]+cost[i-2],cache[i-1]+cost[i-1]);}return cache[cost.size()];}

*873. Length of Longest Fibonacci Subsequence

思路

定义 f [ i ] [ j ] f[i][j] f[i][j]为使用 a r r [ i ] arr[i] arr[i] 为斐波那契数列的最后一位,使用 a r r [ j ] arr[j] arr[j] 为倒数第二位(即 a r r [ i ] arr[i] arr[i] 的前一位)时的最长数列长度。

不失一般性考虑 f [ i ] [ j ] f[i][j] f[i][j]该如何计算,首先根据斐波那契数列的定义,我们可以直接算得 a r r [ j ] arr[j] arr[j] 前一位的值为 a r r [ i ] − a r r [ j ] arr[i]−arr[j] arr[i]arr[j],而快速得知 a r r [ i ] − a r r [ j ] arr[i]−arr[j] arr[i]arr[j]值的坐标 t t t,可以利用 arr 的严格单调递增性质,使用「哈希表」对坐标进行转存,若坐标 t t t存在,并且符合 t < j t<j t<j,说明此时至少凑成了长度为 333 的斐波那契数列,同时结合状态定义,可以使用 f [ j ] [ t ] f[j][t] f[j][t]来更新 f [ i ] [ j ] f[i][j] f[i][j],即有状态转移方程:
f [ i ] [ j ] = m a x ⁡ ( 3 , f [ j ] [ t ] + 1 ) f [ i ] [ j ] = max ⁡ ( 3 , f [ j ] [ t ] + 1 ) f[i][j]=max⁡(3,f[j][t]+1)f[i][j] = \max(3, f[j][t] + 1) f[i][j]=max(3,f[j][t]+1)f[i][j]=max(3,f[j][t]+1)
同时,当我们「从小到大」枚举 iii,并且「从大到小」枚举 j j j 时,我们可以进行如下的剪枝操作:

  • 可行性剪枝:当出现 a r r [ i ] − a r r [ j ] > = a r r [ j ] arr[i]−arr[j]>=arr[j] arr[i]arr[j]>=arr[j],说明即使存在值为 a r r [ i ] − a r r [ j ] arr[i]−arr[j] arr[i]arr[j]的下标 t t t,根据 arr 单调递增性质,也不满足 t < j < i t<j<i t<j<i 的要求,且继续枚举更小的 j j j ,仍然有 a r r [ i ] − a r r [ j ] > = a r r [ j ] arr[i]−arr[j]>=arr[j] arr[i]arr[j]>=arr[j],仍不合法,直接 break 掉当前枚举 j j j的搜索分支;
  • 最优性剪枝:假设当前最大长度为 ans,只有当 j + 2 > a n s j+2>ans j+2>ans,我们才有必要往下搜索, j + 2 j+2 j+2 的含义为以 a r r [ j ] arr[j] arr[j] 为斐波那契数列倒数第二个数时的理论最大长度。

代码

    public int lenLongestFibSubseq(int[] arr) {int ans=0;HashMap<Integer,Integer> finder=new HashMap<>();for (int i = 0; i < arr.length; i++) {finder.put(arr[i],i);}int[][] cache=new int[arr.length][arr.length];for (int i = 2; i < arr.length; i++) {for (int j = i-1; j >= 1; j--) {int residual=arr[i]-arr[j];if (residual>=arr[j]){break;}if (finder.containsKey(arr[i]-arr[j])){cache[i][j]=Math.max(3,cache[j][finder.get(residual)]+1);ans=Math.max(ans,cache[i][j]);}}}return ans;}

*877. Stone Game

数学解法

事实上,这还是一道很经典的博弈论问题,也是最简单的一类博弈论问题。

为了方便,我们称「石子序列」为石子在原排序中的编号,下标从 1开始。

由于石子的堆数为偶数,且只能从两端取石子。因此先手后手所能选择的石子序列,完全取决于先手每一次决定

证明如下:

由于石子的堆数为偶数,对于先手而言:每一次的决策局面,都能「自由地」选择奇数还是偶数的序列,从而限制后手下一次「只能」奇数还是偶数石子

具体的,对于本题,由于石子堆数为偶数,因此先手的最开始局面必然是[奇数, 偶数],即必然是「奇偶性不同的局面」;当先手决策完之后,交到给后手的要么是[奇数,奇数] 或者 [偶数,偶数],即必然是「奇偶性相同的局面」;后手决策完后,又恢复「奇偶性不同的局面」交回到先手 …

不难归纳推理,这个边界是可以应用到每一个回合。

因此先手只需要在进行第一次操作前计算原序列中「奇数总和」和「偶数总和」哪个大,然后每一次决策都「限制」对方只能选择「最优奇偶性序列」的对立面即可

同时又由于所有石子总和为奇数,堆数为偶数,即没有平局,所以先手必胜。

    bool stoneGame(vector<int>& piles) {return true;}

动态规划

定义 f[l][r] 为考虑区间 [l,r],在双方都做最好选择的情况下,先手与后手的最大得分差值为多少。

那么 f[1][n] 为考虑所有石子,先手与后手的得分差值:

  • f [ 1 ] [ n ] > 0 f[1][n]>0 f[1][n]>0,则先手必胜,返回 True
  • f [ 1 ] [ n ] < 0 f[1][n]<0 f[1][n]<0,则先手必败,返回 False

不失一般性的考虑 f [ l ] [ r ] f[l][r] f[l][r]如何转移。根据题意,只能从两端取石子(令 piles 下标从 1 开始),共两种情况:

  • 从左端取石子,价值为piles[l - 1];取完石子后,原来的后手变为先手,从 [l+1,r] 区间做最优决策,所得价值为 f[l+1][r]。因此本次先手从左端点取石子的话,双方差值为:
    p i l e s [ l − 1 ] − f [ l + 1 ] [ r ] piles[l−1]−f[l+1][r] piles[l1]f[l+1][r]
  • 从右端取石子,价值为 piles[r−1];取完石子后,原来的后手变为先手,从[l,r−1] 区间做最优决策,所得价值为 f[l][r−1]。因此本次先手从右端点取石子的话,双方差值为:
    p i l e s [ r − 1 ] − f [ l ] [ r − 1 ] piles[r−1]−f[l][r−1] piles[r1]f[l][r1]

双方都想赢,都会做最优决策(即使自己与对方分差最大)。因此 f [ l ] [ r ] f[l][r] f[l][r] 为上述两种情况中的最大值。

根据动态规划的状态转移方程,计算 dp [ i ] [ j ] \textit{dp}[i][j] dp[i][j] 需要使用 dp[i+1][j]dp[i][j−1]的值,即区间 [i+1,j][i,j−1]的状态值需要在区间[i,j] 的状态值之前计算,因此计算 dp[i][j] 的顺序可以是以下两种。

从小到大遍历每个区间长度,对于每个区间长度依次计算每个区间的状态值。

从大到小遍历每个区间开始下标 i i i,对于每个区间开始下标 i i i 从小到大遍历每个区间结束下标 jjj,依次计算每个区间 [i, j] 的状态值。

计算得到 dp[0][n−1]即为 Alice 与 Bob 的石子数量之差最大值。如果 d p [ 0 ] [ n − 1 ] > 0 dp[0][n−1]>0 dp[0][n1]>0,则 Alice 赢得游戏,返回true,否则 Bob 赢得游戏,返回 false。

class Solution {public boolean stoneGame(int[] ps) {int n = ps.length;int[][] f = new int[n + 2][n + 2]; for (int len = 1; len <= n; len++) { // 枚举区间长度for (int l = 1; l + len - 1 <= n; l++) { // 枚举左端点int r = l + len - 1; // 计算右端点int a = ps[l - 1] - f[l + 1][r];int b = ps[r - 1] - f[l][r - 1];f[l][r] = Math.max(a, b);}}return f[1][n] > 0;}
}

*915. Partition Array into Disjoint Intervals

思路

根据题意,我们知道本质是求分割点,使得分割点的「左边的子数组的最大值」小于等于「右边的子数组的最小值」

我们可以先通过一次遍历(从后往前)统计出所有后缀的最小值 min,其中 min[i] = x 含义为下标范围在
[ i , n − 1 ] [i,n−1] [i,n1] n u m s [ i ] nums[i] nums[i]的最小值为 x,然后再通过第二次遍历(从前往后)统计每个前缀的最大值(使用单变量进行维护),找到第一个符合条件的分割点即是答案。

代码

    public int partitionDisjoint(int[] nums) {int[] min=new int[nums.length];int[] max=new int[nums.length];min[nums.length-1]=nums[nums.length-1];for (int i = nums.length-2; i >=0 ; i--) {min[i]=Math.min(min[i+1],nums[i]);}max[0]=nums[0];for (int i = 1; i < nums.length; i++) {max[i]=Math.max(nums[i],max[i-1]);}int ans=0;for (int i = nums.length-2; i >=0; i--) {if (max[i]<=min[i+1]){ans=i;}}return ans+1;}

926. Flip String to Monotone Increasing

思路

根据题意可知,字符有0和1两种状态,所以我们维护一个二维的cache数组来记录每个字符的状况。
cache[i][0]表示第i个字符是0的变换次数,cache[i][1]表示第i个字符是1的变换次数。
根据单调性: 若 s [ i − 1 ] = = 0 s[i-1] == 0 s[i1]==0,s[i]是0或者1都可以保持单调性。
s [ i − 1 ] = = 1 s[i-1] == 1 s[i1]==1,s[i]则必须为1才可以保持单调性(必须满足i-1是1)。
所以

cache[i][0] = cache[i-1][0] + (s[i] == '1' ? 1 : 0);//(自己是0,则前边都是0) 
cache[i][1] = Math.min(cache[i-1][0],cache[i-1][1]) + (s[i] == '0' ? 1 : 0);//(自己是1,前边0或者1都可以) 

最后result = Math.min(cache[i][0],cache[i][1])

代码

    public int minFlipsMonoIncr(String s) {int cache[][]=new int[s.length()][2];char[] arr=s.toCharArray();cache[0][0]=arr[0]=='0'?0:1;cache[0][1]=1-cache[0][0];for (int i = 1; i < arr.length; i++) {cache[i][0]=cache[i-1][0]+(arr[i]=='0'?0:1);cache[i][1]=Math.min(cache[i-1][0],cache[i-1][1])+(arr[i]=='1'?0:1);}return Math.min(cache[s.length()-1][0],cache[s.length()-1][1]);}

相关文章:

算法刷题记录-DP(LeetCode)

746. Min Cost Climbing Stairs 代码 int minCostClimbingStairs(vector<int>& cost) {if (cost.size()<2){return 0;}int cache[cost.size()1];cache[0]0;cache[1]0;for (int i 2; i < cost.size(); i) {cache[i] min(cache[i-2]cost[i-2],cache[i-1]cost[i…...

Springboot整合Neo4J图数据库

1.引入依赖 JDK11&#xff0c; neo4J4.4.23 <parent><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-parent</artifactId><version>2.7.15</version><relativePath/> <!-- lookup parent …...

Unity 2018发布在iOS 16.3偶尔出现画面不动的问题

1&#xff09;Unity 2018发布在iOS 16.3偶尔出现画面不动的问题 2&#xff09;IL2CPP在Xcode下增量编译问题 3&#xff09;帧同步实现PuppetMaster布娃娃系统的问题 这是第351篇UWA技术知识分享的推送&#xff0c;精选了UWA社区的热门话题&#xff0c;涵盖了UWA问答、社区帖子等…...

蠕虫病毒流量分析案例

背景 某供排水集团的网络管理员对其网络的健康状况持认可态度&#xff0c;表示网络运行正常&#xff0c;没有发现异常行为。然而&#xff0c;由于网络环境变得越来越复杂&#xff0c;仅凭借传统的网络经验已经不能全面了解网络情况。因此&#xff0c;我们为供排水集团安装了Ne…...

Transformer(一)—— Attention Batch Normalization

Transformer详解 一、RNN循环神经网络二、seq2seq模型三、Attention&#xff08;注意力机制&#xff09;四、Transformer4.1 self attention4.2 self-attention的变形——Multi-head Self-attention4.3 Masked Attention4.4 Positional Encoding4.5 Batch Normalization4.6 Lay…...

2023高教社杯数学建模C题思路代码 - 蔬菜类商品的自动定价与补货决策

# 1 赛题 在生鲜商超中&#xff0c;一般蔬菜类商品的保鲜期都比较短&#xff0c;且品相随销售时间的增加而变差&#xff0c; 大部分品种如当日未售出&#xff0c;隔日就无法再售。因此&#xff0c; 商超通常会根据各商品的历史销售和需 求情况每天进行补货。 由于商超销售的蔬菜…...

【C++漂流记】一文搞懂类与对象的封装

本篇文章主要说明了类与对象中封装的有关知识&#xff0c;包括属性和行为作为整体、访问权限、class与struct的区别、成员属性的私有化&#xff0c;希望这篇文章可以帮助你更好的了解类与对象这方面的知识。 文章目录 一、属性和行为作为整体二、访问权限三、class与struct的区…...

ctfshow 反序列化

PHP反序列化前置知识 序列化和反序列化 对象是不能在字节流中传输的&#xff0c;序列化就是把对象转化为字符串以便存储和传输&#xff0c;反序列化就是将字符串转化为对象 魔术方法 __construct() //构造&#xff0c;当对象new时调用 __wakeup() //执行unserialize()时&am…...

数据结构:线性表之-单向链表(无头)

目录 什么是单向链表 顺序表和链表的区别和联系 顺序表&#xff1a; 链表&#xff1a; 链表表示(单项)和实现 1.1 链表的概念及结构 1.2单链表(无头)的实现 所用文件 将有以下功能&#xff1a; 链表定义 创建新链表元素 尾插 头插 尾删 头删 查找-给一个节点的…...

为IT服务台构建自定义Zia操作

Zia是manageengine的商业人工智能助手&#xff0c;是ServiceDesk Plus Cloud的虚拟会话支持代理。使用Zia&#xff0c;您可以优化帮助台管理&#xff0c;还可以缩小最终用户与其帮助台之间的差距&#xff0c;Zia通过执行预配置的操作来帮助用户完成他们的服务台任务。 例如&…...

【C/C++】BMP格式32位转24位

问题 如题 解决方法 bmp文件格式参考:【C/C++】BITMAP格式分析_vc++ bitmap头文件_sunriver2000的博客-CSDN博客BITMAP文件大体上分成四个部分,如下表所示。文件部分长度(字节)位图文件头 Bitmap File Header14位图信息数据头 Bitmap Info Header40调色板 Palette4*n (n≥…...

合宙Air724UG LuatOS-Air LVGL API控件-滑动条 (Slider)

滑动条 (Slider) 滑动条看起来和进度条是有些是有些像&#xff0c;但不同的是滑动条可以进行数值选择。 示例代码 -- 回调函数 slider_event_cb function(obj, event)if event lvgl.EVENT_VALUE_CHANGED then local val (lvgl.slider_get_value(obj) or "0")..&…...

SQLAlchemy 封装的工具类,数据库pgsql(数据库连接池)

1.SQLAlchemy是什么&#xff1f; SQLAlchemy 是 Python 著名的 ORM 工具包。通过 ORM&#xff0c;开发者可以用面向对象的方式来操作数据库&#xff0c;不再需要编写 SQL 语句。 SQLAlchemy 支持多种数据库&#xff0c;除 sqlite 外&#xff0c;其它数据库需要安装第三方驱动。…...

【Git】Git 基础

Git 基础 参考 Git 中文文档 — https://git-scm.com/book/zh/v2 1.介绍 Git 是目前世界上最先进的分布式版本控制系统&#xff0c;有这么几个特点&#xff1a; 分布式&#xff1a;是用来保存工程源代码历史状态的命令行工具保存点&#xff1a;保存点可以追溯源码中的文件…...

腾讯云AI绘画:探究AI创意与技术的新边界

目录 一、2023的“网红词汇”——AI绘画二、智能文生图1、智能文生图的应用场景2、风格和配置的多样性3、输入一段话&#xff0c;腾讯云AI绘画给你生成一张图4、文本描述生成图像&#xff0c;惊艳全场 三、智能图生图&#xff1a;重新定义图像美学1、智能图生图的多元应用场景2…...

离线数仓同步数据1

用户行为表数据同步 2.1.4 日志消费Flume测试 [gpbhadoop104 ~]$ cd /opt/module/flume/ [gpbhadoop104 flume]$ cd job/ [gpbhadoop104 job]$ rm file_to_kafka.confcom.atguigu.gmall.flume.interceptor.TimestampInterceptor$Builder #定义组件 a1.sourcesr1 a1.channelsc1…...

c语言开篇---跟着视频学C语言

标识符 标识符必须声明定义&#xff0c;可以是变量、函数或其他实体。 Int是标识符吗&#xff1f; 不是&#xff0c;int是c语言关键词&#xff0c;不是随意命名的 C语言关键词如下&#xff1a; 常量 不需要被声明&#xff0c;不能赋值更改。 printf函数 printf是由print打印…...

本地yum源-如学

学不学&#xff1f; 如学&#xff5e; 到底学不学&#xff1f; 如学&#xff5e; 学&#xff1f; 如学&#xff5e; 配置本地的镜像yum 使用到的 rpm 包 是根据centos8 里面自带的 在 /dev/cdrom 中包含着 一些系统自带的 rpm # 先将 /dev/cdrom 设备进行挂载 mkdir /up # 在…...

【实训】“宅急送”订餐管理系统(程序设计综合能力实训)

&#x1f440;樊梓慕&#xff1a;个人主页 &#x1f3a5;个人专栏&#xff1a;《C语言》《数据结构》《蓝桥杯试题》《LeetCode刷题笔记》《实训项目》 &#x1f31d;每一个不曾起舞的日子&#xff0c;都是对生命的辜负 前言 大一小学期&#xff0c;我迎来了人生中的第一次实训…...

openeuler上安装polarismesh集群

1、安装MySQL数据库 数据库连接地址10.10.10.168 用户root 密码123456 MySQL安装参考搭建DSS环境&#xff08;六&#xff09;之安装基础环境MySQL_linux安装dss_青春不流名的博客-CSDN博客 2、安装Redis集群 IPResid PORTSentinel PORTPASSWORDCluster NAME10.10.10.110637…...

C++初阶-list的底层

目录 1.std::list实现的所有代码 2.list的简单介绍 2.1实现list的类 2.2_list_iterator的实现 2.2.1_list_iterator实现的原因和好处 2.2.2_list_iterator实现 2.3_list_node的实现 2.3.1. 避免递归的模板依赖 2.3.2. 内存布局一致性 2.3.3. 类型安全的替代方案 2.3.…...

云计算——弹性云计算器(ECS)

弹性云服务器&#xff1a;ECS 概述 云计算重构了ICT系统&#xff0c;云计算平台厂商推出使得厂家能够主要关注应用管理而非平台管理的云平台&#xff0c;包含如下主要概念。 ECS&#xff08;Elastic Cloud Server&#xff09;&#xff1a;即弹性云服务器&#xff0c;是云计算…...

《Qt C++ 与 OpenCV:解锁视频播放程序设计的奥秘》

引言:探索视频播放程序设计之旅 在当今数字化时代,多媒体应用已渗透到我们生活的方方面面,从日常的视频娱乐到专业的视频监控、视频会议系统,视频播放程序作为多媒体应用的核心组成部分,扮演着至关重要的角色。无论是在个人电脑、移动设备还是智能电视等平台上,用户都期望…...

AtCoder 第409​场初级竞赛 A~E题解

A Conflict 【题目链接】 原题链接&#xff1a;A - Conflict 【考点】 枚举 【题目大意】 找到是否有两人都想要的物品。 【解析】 遍历两端字符串&#xff0c;只有在同时为 o 时输出 Yes 并结束程序&#xff0c;否则输出 No。 【难度】 GESP三级 【代码参考】 #i…...

Linux相关概念和易错知识点(42)(TCP的连接管理、可靠性、面临复杂网络的处理)

目录 1.TCP的连接管理机制&#xff08;1&#xff09;三次握手①握手过程②对握手过程的理解 &#xff08;2&#xff09;四次挥手&#xff08;3&#xff09;握手和挥手的触发&#xff08;4&#xff09;状态切换①挥手过程中状态的切换②握手过程中状态的切换 2.TCP的可靠性&…...

工程地质软件市场:发展现状、趋势与策略建议

一、引言 在工程建设领域&#xff0c;准确把握地质条件是确保项目顺利推进和安全运营的关键。工程地质软件作为处理、分析、模拟和展示工程地质数据的重要工具&#xff0c;正发挥着日益重要的作用。它凭借强大的数据处理能力、三维建模功能、空间分析工具和可视化展示手段&…...

多模态大语言模型arxiv论文略读(108)

CROME: Cross-Modal Adapters for Efficient Multimodal LLM ➡️ 论文标题&#xff1a;CROME: Cross-Modal Adapters for Efficient Multimodal LLM ➡️ 论文作者&#xff1a;Sayna Ebrahimi, Sercan O. Arik, Tejas Nama, Tomas Pfister ➡️ 研究机构: Google Cloud AI Re…...

服务器--宝塔命令

一、宝塔面板安装命令 ⚠️ 必须使用 root 用户 或 sudo 权限执行&#xff01; sudo su - 1. CentOS 系统&#xff1a; yum install -y wget && wget -O install.sh http://download.bt.cn/install/install_6.0.sh && sh install.sh2. Ubuntu / Debian 系统…...

安全突围:重塑内生安全体系:齐向东在2025年BCS大会的演讲

文章目录 前言第一部分&#xff1a;体系力量是突围之钥第一重困境是体系思想落地不畅。第二重困境是大小体系融合瓶颈。第三重困境是“小体系”运营梗阻。 第二部分&#xff1a;体系矛盾是突围之障一是数据孤岛的障碍。二是投入不足的障碍。三是新旧兼容难的障碍。 第三部分&am…...

mac 安装homebrew (nvm 及git)

mac 安装nvm 及git 万恶之源 mac 安装这些东西离不开Xcode。及homebrew 一、先说安装git步骤 通用&#xff1a; 方法一&#xff1a;使用 Homebrew 安装 Git&#xff08;推荐&#xff09; 步骤如下&#xff1a;打开终端&#xff08;Terminal.app&#xff09; 1.安装 Homebrew…...