文章目录

  • 1. 题目
    • 1.1 示例
    • 1.2 说明
    • 1.3 提示
    • 1.4 进阶
  • 2. 解法一(动态规划)
    • 2.1 分析
      • 2.1.1 定义状态
      • 2.1.2 初始化状态
      • 2.1.3 状态转移
      • 2.1.4 返回结果
    • 2.2 解答
    • 2.3 复杂度
  • 3. 解法二(耐心排序)
    • 3.1 分析
    • 3.2 解答
    • 3.3 复杂度

1. 题目

给定一个未排序的整数数组,找到最长递增子序列的个数。

1.1 示例

  • 示例 1 1 1 :
  • 输入: [1, 3, 5, 4, 7]
  • 输出: 2 2 2
  • 解释: 有两个最长递增子序列,分别是 [1, 3, 4, 7][1, 3, 5, 7]
  • 示例 2 2 2 :
  • 输入: [2, 2, 2, 2, 2]
  • 输出: 5 5 5
  • 解释: 最长递增子序列的长度是 1 1 1,并且存在 5 5 5 个子序列的长度为 1 1 1 ,因此输出 5 5 5 。

1.2 说明

  • 来源: 力扣(LeetCode)
  • 链接: https://leetcode-cn.com/problems/number-of-longest-increasing-subsequence

1.3 提示

给定的数组长度不超过 2000 2000 2000 并且结果一定是 32 32 32 位有符号整数。

1.4 进阶

2. 解法一(动态规划)

2.1 分析

  • 作者: edelweisskoko

2.1.1 定义状态

  • dp[i]:到 nums[i] 为止的最长递增子序列长度;
  • count[i]:到 nums[i] 为止的最长递增子序列个数。

2.1.2 初始化状态

  • dp = [1] * n:代表最长递增子序列的长度至少为 1 1 1 ;
  • count = [1] * n:代表最长递增子序列的个数至少为 1 1 1 。

2.1.3 状态转移

对于每一个数 nums[i],看在它之前的数 nums[j] ( 0 ≤ j < i 0 \le j \lt i 0≤j<i)是否比当前数 nums[i] 小:

  • 如果 nums[i] > nums[j],那么相当于到 nums[j] 为止的最长递增子序列长度到 nums[i] 增加了 1 1 1,到 nums[i] 为止的最长递增子序列长度就变成了 dp[i] = dp[j] + 1
  • 但是因为满足 nums[i] > nums[j]nums[j] 不止一个,dp[i] 应该取这些 dp[j] + 1 的最大值,并且这些 dp[j] + 1 还会有相等的情况,一旦相等,到 nums[i] 为止的最长递增子序列个数就应该增加了。因此,具体的状态转移如下,在 nums[i] > nums[j] 的大前提下:
    • 如果 dp[j] + 1 > dp[i] ,说明最长递增子序列的长度增加了,dp[i] = dp[j] + 1,长度增加,数量不变 count[i] = count[j]
    • 如果 dp[j] + 1 == dp[i],说明最长递增子序列的长度并没有增加,但是出现了长度一样的情况,数量增加 count[i] += count[j]

2.1.4 返回结果

最终,将所有最长递增子序列的个数加在一起即为最终结果。

2.2 解答

from typing import Listclass Solution:@classmethoddef find_num_of_lis(cls, nums: List[int]) -> int:dp = [1] * len(nums)count = [1] * len(nums)max_length = 0num = 0for i in range(len(nums)):for j in range(i):if nums[i] > nums[j]:if dp[j] + 1 > dp[i]:dp[i] = dp[j] + 1count[i] = count[j]elif dp[j] + 1 == dp[i]:count[i] += count[j]max_length = max(dp)for k in range(len(nums)):if dp[k] == max_length:num += count[k]return numdef main():# nums = [1, 3, 5, 4, 7]nums = [2, 2, 2, 2, 2]sln = Solution()print(sln.find_num_of_lis(nums))  # 5if __name__ == '__main__':main()
  • 执行用时: 876 ms , 在所有 Python3 提交中击败了 82.00% 的用户;
  • 内存消耗: 15.1 MB , 在所有 Python3 提交中击败了 86.19% 的用户。

实际上,最后用于返回结果的代码可以进一步简化:

from typing import Listclass Solution:@classmethoddef find_num_of_lis(cls, nums: List[int]) -> int:dp = [1] * len(nums)count = [1] * len(nums)num = 0for i in range(len(nums)):for j in range(i):if nums[i] > nums[j]:if dp[j] + 1 > dp[i]:dp[i] = dp[j] + 1count[i] = count[j]elif dp[j] + 1 == dp[i]:count[i] += count[j]max_length = max(dp)return sum(c for i, c in enumerate(count) if dp[i] == max_length)def main():# nums = [1, 3, 5, 4, 7]nums = [2, 2, 2, 2, 2]sln = Solution()print(sln.find_num_of_lis(nums))  # 5if __name__ == '__main__':main()

2.3 复杂度

  • 时间复杂度: O ( n 2 ) O(n^2) O(n2) 。其中 n n n 是 nums 的长度。
  • 空间复杂度: O ( n ) O(n) O(n),dpcount 所用的空间。

3. 解法二(耐心排序)

  • 作者: Dmitry DBabichev

3.1 分析

3.2 解答

3.3 复杂度

【LeetCode 动态规划专项】最长递增子序列的个数(673)相关推荐

  1. leetcode算法题-- 最长递增子序列的个数★

    原题链接:https://leetcode-cn.com/problems/number-of-longest-increasing-subsequence/ 相关题目:最长上升子序列 lengths ...

  2. 动态规划应用--最长递增子序列 LeetCode 300

    文章目录 1. 问题描述 2. 解题思路 2.1 动态规划 2.2 二分查找 1. 问题描述 有一个数字序列包含n个不同的数字,如何求出这个序列中的最长递增子序列长度?比如2,9,3,6,5,1,7这 ...

  3. 112. Leetcode 673. 最长递增子序列的个数 (动态规划-子序列问题)

    步骤一.确定状态: 确定dp数组及下标含义 dp[i]表示以nums[i]结尾的数组最长递增子序列的长度, count数组, count[i]记 录以nums[i]结尾的数组,最长递增子序列的个数. ...

  4. LeetCode 673. 最长递增子序列的个数(DP)

    1. 题目 给定一个未排序的整数数组,找到最长递增子序列的个数. 示例 1: 输入: [1,3,5,4,7] 输出: 2 解释: 有两个最长递增子序列,分别是 [1, 3, 4, 7] 和[1, 3, ...

  5. leetcode - 673. 最长递增子序列的个数

    给定一个未排序的整数数组,找到最长递增子序列的个数. 示例 1: 输入: [1,3,5,4,7] 输出: 2 解释: 有两个最长递增子序列,分别是 [1, 3, 4, 7] 和[1, 3, 5, 7] ...

  6. LeetCode 673. 最长递增子序列的个数

    LeetCode 673. 最长递增子序列的个数 文章目录 LeetCode 673. 最长递增子序列的个数 题目描述 一.解题关键词 二.解题报告 1.思路分析 2.时间复杂度 3.代码示例 2.知 ...

  7. [Leetcode]673. 最长递增子序列的个数

    给定一个未排序的整数数组 nums , 返回最长递增子序列的个数 . 注意 这个数列必须是 严格 递增的. 示例 1: 输入: [1,3,5,4,7] 输出: 2 解释: 有两个最长递增子序列,分别是 ...

  8. [Swift]LeetCode673. 最长递增子序列的个数 | Number of Longest Increasing Subsequence

    ★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★ ➤微信公众号:山青咏芝(shanqingyongzhi) ➤博客园地址:山青咏芝(https://www.cnblog ...

  9. 最长递增子序列的个数Python解法

    给定一个未排序的整数数组,找到最长递增子序列的个数. 列: 输入: [1,3,5,4,7] 输出: 2 解释: 有两个最长递增子序列,分别是 [1, 3, 4, 7] 和[1, 3, 5, 7]. # ...

最新文章

  1. 【OpenCV 4开发详解】图像透视变换
  2. 基于深度学习的视觉三维重建研究总结
  3. 麦子学院彭亮python基础_麦子学院python
  4. python编程入门电子书下载-Python编程基础如何快速入门?“附电子书下载”
  5. 在64位Windows 7 激活BitDefender Internet Security 2010
  6. 1.10 throws和throw:声明和抛出异常
  7. 真是一分钱一分货 NVme SSD都有哪些优势?
  8. 使用pycaffe读取caffemodel参数(保存到txt文件)
  9. go 语言 mysql_Go语言基础之操作MySQL
  10. 【Kafka】failed due to invalid credentials with broker older than 1.1.0
  11. 深入浅出设计模式(一):单例模式
  12. intptr java_[转载]C#中int和IntPtr相互转换
  13. Excel高级应用专题-数组公式
  14. Android碎片化问题
  15. 鸿鹄系统和鸿蒙系统的区别,华为鸿蒙系统和全新的鸿鹄处理器将于8月9日正式发布,荣耀首发...
  16. 一个本科渣渣是怎么逆袭从咸鱼到Offer收割机的?绝对干货
  17. 如何处理json数据
  18. day2学python 数据类型+深浅拷贝+循环
  19. Dockerfile制作镜像
  20. User root is not allowed to impersonate anonymous

热门文章

  1. CAS:1347750-20-2,NH2-PEG-SH,Amine-PEG-Thiol,氨基-聚乙二醇-巯基供应
  2. 这个大学生,抢先go2实现了go的泛型
  3. 动态捕捉(四)深度图像基础知识
  4. 谷牛期权涨跌参半 原油、燃油涨潮1%
  5. Elasticsearch启动遇到nofile、nproc、jvm等报错
  6. Ubuntu下Pycharm切换中文输入法无法输入中文解决方法
  7. Doris 平滑缩容,Be 节点卡住不动
  8. Android--OpenGL坐标系
  9. mysql 自定义函数报错_Mysql自定义函数报错解决方法
  10. ANR实战案例3 - 应用在部分低端机ANR优化案例