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

【LeetCode】动态规划—646. 最长数对链(附完整Python/C++代码)

动态规划—646. 最长数对链

  • 前言
  • 题目描述
  • 基本思路
    • 1. 问题定义
    • 2. 理解问题和递推关系
    • 3. 解决方法
      • 3.1 动态规划方法
      • 3.2 贪心方法
    • 4. 进一步优化
    • 5. 小总结
  • 代码实现
    • Python
      • Python3代码实现
      • Python 代码解释
    • C++
      • C++代码实现
      • C++ 代码解释
  • 总结

前言

在这个问题中,我们需要找到可以形成的最长数对链。数对 (a, b) 的链要求 a < b,并且数对链的连接需要满足 b1 < a2。这类似于寻找最长递增子序列的问题,可以通过动态规划或者贪心算法来解决。

贪心算法通过将数对按右端排序,并逐步选择满足条件的数对,能够在更短的时间内解决问题。本文将详细介绍动态规划和贪心策略,并提供 Python 和 C++ 代码示例,帮助你理解并掌握这一问题的解法。

题目描述

在这里插入图片描述

基本思路

1. 问题定义

给定一组数对 pairs,其中每个数对由两个整数组成 (a, b),并且 a < b。一条 数对链 是指可以将数对 (a1, b1)(a2, b2) 连接起来,满足 b1 < a2。你需要找到最长的数对链。

2. 理解问题和递推关系

这个问题类似于 最长递增子序列 的问题。我们需要选择数对,并构建满足条件的数对链,使得链的长度最大化。两种解法是常见的:

动态规划:对于每一个数对,检查它之前的所有数对是否满足 b1 < a2,如果满足,则更新当前数对能构成的最长链。
贪心策略:通过对数对的右端 b 进行排序,贪心地选择每一个数对,确保尽可能形成最长的数对链。

  • 动态规划方法
    1. 首先,将数对按照左端 a 进行升序排序,或者按照右端 b 进行升序排序。
    2. 定义 dp[i] 为以第 i 个数对为结尾的最长数对链的长度。
    3. 对于每一个数对 pairs[i],遍历之前的所有数对 pairs[j],检查 pairs[j][1] < pairs[i][0],即数对是否可以连接。如果可以,则更新 d p [ i ] = m x ( d p [ i ] , d p [ j ] + 1 ) dp[i] = mx(dp[i], dp[j] + 1) dp[i]=mx(dp[i],dp[j]+1)
    4. 最终,答案为 max(dp),即最长数对链的长度。
  • 贪心方法
    1. 首先,将数对按照右端 b 进行升序排序。
    2. 贪心地选择每个数对,在选择时保证其左端 a 大于上一个数对的右端 b,以确保形成最长链。
    3. 最终计数即为链的长度。

3. 解决方法

3.1 动态规划方法

  • 排序后,使用动态规划求解最优解。遍历每个数对,更新每个数对能够形成的最长链。

3.2 贪心方法

  • 排序后,通过贪心策略选择尽可能多的数对来构成最长链。

4. 进一步优化

  • 贪心方法 的时间复杂度是 O ( n l o g n ) O(n log n) O(nlogn),因为排序需要 O ( n l o g n ) O(n log n) O(nlogn) 的时间,而遍历一遍数对仅需要 O ( n ) O(n) O(n) 的时间。相比之下,动态规划的时间复杂度为 O ( n 2 ) O(n^2) O(n2),适合小规模数据。贪心方法在时间效率上更优。

5. 小总结

  • 动态规划方法可以通过递推公式解决,但时间复杂度较高,适合较小规模的输入。
  • 贪心方法是更优的选择,能够在 O ( n l o g n ) O(n log n) O(nlogn) 的时间复杂度内解决问题,适用于大规模输入。

以上就是最长数对链问题的基本思路。

代码实现

Python

Python3代码实现

class Solution:def findLongestChain(self, pairs: list[list[int]]) -> int:# 按照数对的第二个元素(右端点)进行升序排序pairs.sort(key=lambda x: x[1])# 初始化计数器和当前数对的结束位置cur_end = float('-inf')count = 0# 遍历每个数对for pair in pairs:# 如果当前数对可以与上一个数对连接if pair[0] > cur_end:cur_end = pair[1]  # 更新结束位置count += 1  # 更新数对链长度return count

Python 代码解释

  • 排序:首先按照数对的右端 b 进行升序排序,以便我们可以贪心地选择更多的数对。
  • 贪心选择:遍历每个数对,检查其左端 a 是否大于当前链的结束位置 cur_end,如果满足条件,则更新链的结束位置,并增加链的长度。
  • 返回结果:最终返回最长数对链的长度。

C++

C++代码实现

class Solution {
public:int findLongestChain(vector<vector<int>>& pairs) {// 按照数对的第二个元素(右端点)进行升序排序sort(pairs.begin(), pairs.end(), [](vector<int>& a, vector<int>& b) {return a[1] < b[1];});int cur_end = INT_MIN;  // 当前数对链的结束位置int count = 0;  // 初始化数对链的长度// 遍历每个数对for (const auto& pair : pairs) {if (pair[0] > cur_end) {  // 如果当前数对可以连接cur_end = pair[1];  // 更新链的结束位置count++;  // 增加链的长度}}return count;  // 返回最长数对链的长度}
};

C++ 代码解释

  • 排序:对数对的右端进行升序排序,方便后续的贪心选择。
  • 贪心选择:通过遍历数对,判断是否可以将当前数对加入链中。如果当前数对的左端大于前一个数对的右端,就可以将其加入,并更新链的长度。
  • 返回结果:最终返回最长数对链的长度。

总结

  • 动态规划方法能够通过递推计算每个数对的最长链,但时间复杂度较高,为 O ( n 2 ) O(n^2) O(n2)
  • 贪心算法通过排序和逐步选择,能够在 O ( n l o g n ) O(n log n) O(nlogn) 的时间内解决问题,是更高效的解法。
  • 本文提供的 Python 和 C++ 实现展示了贪心算法的高效性,希望能够帮助你解决类似的数对链问题。

相关文章:

【LeetCode】动态规划—646. 最长数对链(附完整Python/C++代码)

动态规划—646. 最长数对链 前言题目描述基本思路1. 问题定义2. 理解问题和递推关系3. 解决方法3.1 动态规划方法3.2 贪心方法 4. 进一步优化5. 小总结 代码实现PythonPython3代码实现Python 代码解释 CC代码实现C 代码解释 总结 前言 在这个问题中&#xff0c;我们需要找到可…...

数字媒体产业园区:创新资源集聚,助力企业成长

在当今数字化浪潮汹涌的时代&#xff0c;数字媒体产业园区作为创意与技术的交汇点&#xff0c;正以其独特的魅力和无限的潜力&#xff0c;成为助力企业成长的重要平台。其中&#xff0c;“数字媒体产业园区”以其创新资源的集聚效应&#xff0c;为入驻企业提供了广阔的发展空间…...

【Linux】来查看当前系统的架构

使用 uname 命令 uname -m 使用 arch 命令 arch 查看 /proc/cpuinfo 文件 查找 model name 或 Processor 字段。 cat /proc/cpuinfo 使用 lscpu 命令 lscpu...

QT中的信号槽

1.解释说明 1- qt中一般是使用信号槽来绑定对应的事件 2- 可以在初始化中调用connect来调用 3- 这里分别用头文件、源文件、界面文件去写示例 2.头文件.h #ifndef MAINWINDOW_H #define MAINWINDOW_H#include <QMainWindow>QT_BEGIN_NAMESPACE namespace Ui { class Mai…...

域名怎么转让给别人?

域名怎么转让给别人?许多企业和个人在发展过程中可能会选择转让域名&#xff0c;无论是因为业务重组、品牌更换&#xff0c;还是为了实现经济利益。那么&#xff0c;如何将域名顺利转让给他人呢?本文将详细介绍域名转让的步骤和注意事项。 一、了解域名转让的基本概念 域名…...

计算机网络思维导图

计算机网络 网络层 概述 主要任务 实现网路互连&#xff0c;进而实现数据包在各网络之间的传输 解决问题 向运输层提供可靠传输/不可靠传输的服务网络层寻址问题路由选择问题 英特网时使用最多的互联网&#xff0c;使用TCP/IP协议栈 网络层使用网际协议IP&#xff0c;时整个…...

07.useDefault

在 React 应用开发中,处理状态的默认值和空值情况是一个常见需求。useDefault 钩子提供了一种优雅的方式来管理状态,同时为空值(null 或 undefined)提供默认回退值。这个自定义钩子不仅简化了状态管理,还提高了代码的可读性和健壮性。以下是如何实现和使用这个自定义钩子:…...

git更加详细和灵活的提交过程,附带如何配置. gitignore来忽略部分文件的提交。

本套流程可以控制提交的代码是哪些&#xff0c;比直接使用git add . 更灵活&#xff0c;比如在项目中&#xff0c;一些文件不能通过.gitignore进行尽职提交&#xff0c;那么就需要使用本方法来手动控制是否提交&#xff0c;缺点就是相对麻烦一些。 git status//查看从当前工作…...

使用正则表达式删除文本的奇数行或者偶数行

用智谱清言和kimi搜出来的结果都没法在notepad生效&#xff0c;后面在overflow上找到的答案比较靠谱。 查找&#xff1a;^[^\n]*\n([^\n]*) 替换&#xff1a;\1 删除偶数行 查找&#xff1a;^([^\n]*)\n[^\n]* 替换&#xff1a;\1 代码解释 ^&#xff1a;这个符号代表字符…...

YOLOv10改进策略【注意力机制篇】| CVPR2024 CAA上下文锚点注意力机制

一、本文介绍 本文记录的是基于CAA注意力模块的YOLOv10目标检测改进方法研究。在远程遥感图像或其他大尺度变化的图像中目标检测任务中,为准确提取其长距离上下文信息,需要解决大目标尺度变化和多样上下文信息时的不足的问题。CAA能够有效捕捉长距离依赖,并且参数量和计算量…...

Unity修改鼠标图片【超简单】

1.向Unity导入需要修改的鼠标图片&#xff0c;在Unity内设置图片的Texture Type为Cursor。 2.编写代码 [SerializeField] Texture2D mouseTex;//放图片 void Start() {Cursor.SetCursor(mouseTex, Vector2.zero, CursorMode.Auto); }3.代码挂载在某物体&#xff08;或者随便哪…...

windows C++-创建数据流代理(三)

以下示例展示了 log_agent 类&#xff0c;它类似于 dataflow_agent 类。 log_agent 类实现异步记录代理&#xff0c;用于将日志消息写入文件和控制台。 log_agent 类使应用程序能够将消息分类为信息性、警告或错误消息。 它还使应用程序能够指定每个日志类别是写入文件、控制台…...

C语言学习-循环嵌套打印字母金字塔

前言 最近博主也是在努力的学习C语言&#xff0c;在学习的过程当中碰到了一个对我来说的“难题”&#xff0c;足足控了我有半小时&#xff0c;不过这个问题也是挺有趣的&#xff0c;我也就借着本道题目来写一篇文章和大家交流交流 准备工作 vs2022(其他编辑器当然也可以)c语…...

探索CI/CD:持续集成与持续部署的基本概念

在现代软件开发中&#xff0c;持续集成&#xff08;CI&#xff09;和持续部署&#xff08;CD&#xff09;已经成为提高开发效率和产品质量的关键实践。本文将详细介绍CI/CD的基本概念、优势以及如何在实际项目中实施CI/CD。 一、什么是持续集成&#xff08;CI&#xff09;&…...

大厂面试真题:说一说CMS和G1

CMS垃圾回收器四个主要步骤 初始标记阶段&#xff08;Initial Mark Phase&#xff09; 目的&#xff1a;标记老年代中所有从GC Roots直接可达的对象。特点&#xff1a;此阶段会导致STW&#xff08;Stop The World&#xff09;&#xff0c;即暂停应用程序的执行&#xff0c;但停…...

使用Qt Creator创建项目

个人主页&#xff1a;C忠实粉丝 欢迎 点赞&#x1f44d; 收藏✨ 留言✉ 加关注&#x1f493;本文由 C忠实粉丝 原创 使用Qt Creator创建项目 收录于专栏【Qt开发】 本专栏旨在分享学习Qt的一点学习笔记&#xff0c;欢迎大家在评论区交流讨论&#x1f48c; 目录 温馨提示: 1. 新…...

C++ 与 C 的那些事儿:深度剖析两者区别

在编程的世界里&#xff0c;C 和 C 就像是一对有着紧密血缘关系却又各具特色的兄弟。对于很多初学者或者有一定编程经验的人来说&#xff0c;分清它们之间的差异至关重要。今天&#xff0c;我们就来深入探讨一下 C 和 C 的区别。 <1>、C 是一种静态类型的、编译式的、通…...

学习​Redis 高可用性​

Redis 高可用性&#xff08;High Availability&#xff09;是指在 Redis 系统中实现持续的可用性&#xff0c;即使在发生硬件故障或其他意外情况下&#xff0c;系统仍能保持运行。 Redis 高可用性&#xff08;High Availability&#xff09;是指在 Redis 系统中实现持续的可用性…...

【含开题报告+文档+PPT+源码】基于springBoot+vue超市仓库管理系统的设计与实现

开题报告 随着电子商务的快速发展和物流行业的日益壮大&#xff0c;超市仓库管理系统的重要性也日益凸显。传统的超市仓库管理方式存在许多问题&#xff0c;比如人工操作繁琐、数据统计不准确、管理效率低下等。因此&#xff0c;需要设计和实现一个高效、智能的超市仓库管理系…...

美发店管理革新:SpringBoot系统的应用

1系统概述 1.1 研究背景 随着计算机技术的发展以及计算机网络的逐渐普及&#xff0c;互联网成为人们查找信息的重要场所&#xff0c;二十一世纪是信息的时代&#xff0c;所以信息的管理显得特别重要。因此&#xff0c;使用计算机来管理美发门店管理系统的相关信息成为必然。开发…...

1.1 AI技术全景图:从传统ML到大模型

AI技术全景图&#xff1a;从传统ML到大模型本文适合谁&#xff1a;完全没有AI背景的读者。读完这篇&#xff0c;你会知道"AI/机器学习/深度学习/大模型"这几个词是什么关系&#xff0c;以及你将要学的东西在整个AI世界里处于什么位置。AI发展经历了三个时代——本文带…...

系统架构设计师知识点21-40

21.ABSD方法的三个基础。①功能分解&#xff0c;使用已有的基于模块的内聚与耦合技术②选择架构风格实现质量和业务需求③软件模板使用22.ABSD方法是一个自顶向下&#xff0c;递归细化的方法&#xff0c;软件系统的体系结构通过该方法得到细化&#xff0c;直到能产生软件构件和…...

3分钟搞定!LyricsX让你的macOS音乐播放器拥有完美歌词体验

3分钟搞定&#xff01;LyricsX让你的macOS音乐播放器拥有完美歌词体验 【免费下载链接】LyricsX &#x1f3b6; Ultimate lyrics app for macOS. 项目地址: https://gitcode.com/gh_mirrors/ly/LyricsX 还在为macOS上的音乐播放器找不到合适的歌词而烦恼吗&#xff1f;L…...

微信公众号自动回复避坑指南:如何高效处理用户关键词匹配(PHP版)

微信公众号自动回复进阶实战&#xff1a;PHP高效关键词匹配与消息处理 在运营微信公众号时&#xff0c;自动回复功能是与用户互动的第一道门槛。一个响应迅速、匹配精准的自动回复系统不仅能提升用户体验&#xff0c;还能有效减轻人工客服压力。本文将深入探讨如何用PHP构建一个…...

蓝桥杯 电池分组

...

原子操作的实现原理

在并发编程、操作系统与计算机体系结构中&#xff0c;原子操作是保证数据安全、避免竞态条件的基石。它的核心特性是不可中断、不可分割&#xff0c;操作要么完整执行&#xff0c;要么完全不执行&#xff0c;绝不会出现中间状态。本文将从定义出发&#xff0c;逐层拆解原子操作…...

多租户下的系统基础表设计

多租户下的系统基础表设计在设计 多租户进销存系统&#xff08;SaaS&#xff09; 时&#xff0c;核心是 租户隔离 权限控制 组织结构。 一般推荐的设计是 “租户 → 机构 → 角色 → 用户” 的层级结构&#xff0c;同时所有业务数据都带 tenant_id。租户表&#xff08;Tenant…...

Matlab 2024b 新变化:手把手教你搞定TI C2000代码生成环境(含CCS避坑指南)

Matlab 2024b与TI C2000代码生成环境配置全指南&#xff1a;从版本差异到实战避坑 如果你是一位长期使用Matlab进行TI C2000系列芯片开发的嵌入式工程师&#xff0c;升级到2024b版本后可能会发现&#xff1a;熟悉的配置界面不见了&#xff0c;命令行里输入的命令也不一样了。这…...

MyBatis-Plus中queryWrapper和lambdaQueryWrapper的eq方法实战对比:哪个更适合你的项目?

MyBatis-Plus中QueryWrapper与LambdaQueryWrapper的eq方法深度解析与实战选型指南 在Java持久层框架领域&#xff0c;MyBatis-Plus作为MyBatis的增强工具&#xff0c;其Wrapper条件构造器一直是开发者构建动态SQL的利器。其中eq方法作为最基础也是最常用的条件构造方法&#xf…...

超越单线程:探索MATLAB并行计算与进程间通信的实践路径

1. MATLAB并行计算的本质与局限 很多人第一次接触MATLAB时&#xff0c;都会惊讶于它的单线程特性——当你运行一个耗时计算时&#xff0c;整个界面都会卡住&#xff0c;连命令行都无法输入。这其实源于MATLAB最初的设计哲学&#xff1a;保持简单一致的执行环境。但现代计算任务…...