Leetcode300 最大上升子序列

本文介绍了一种寻找无序整数数组中最长上升子序列的算法,提供了两种解决方案:动态规划O(n^2)和二分O(nlogn)算法。动态规划方法使用dp数组记录每个元素作为子序列结尾时的最长长度,而二分搜索法则通过维护一个有序序列并进行二分查找来优化效率。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

题目描述:
给定一个无序的整数数组,找到其中最长上升子序列的长度,并输出序列。
示例:
输入:[10,9,2,5,3,7,101,18]
输出:4

动态规划O(n2),dp[i]表示以第i个元素作为子序列的最后一个元素所能组成的最长的递增子序列的最长长度。

class Solution:
    def lengthOfLIS(self, num):
        length = len(num)
        dp = [1]*length
        pre = [-1]*length
        for i in range(1, length):
            for j in range(i):
                if num[i] > num[j] and dp[j] + 1 >dp[i]:
                    dp[i] = dp[j] + 1
                    pre[i] = j#pre数组记录每一个 i 的前驱元素,方便记录序列
        _max = 1
        idx = 0
        for i in range(length):
            if dp[i] > _max:
                _max = dp[i]
                idx = i
        print(_max)
        result = []
        while pre[idx] != -1:
            result.append(num[idx])
            idx = pre[idx]          
        result.append(num[idx])
        print(result[::-1])

二分 O(nlogn)算法,dp[i]表示长度为i 的序列的最后一个元素。

class Solution:
    def lengthOfLIS(self, num):
        length = len(num)
        dp = []
        dp.append(num[0])
        for i in range(1, length):
            if num[i] > dp[-1]:
                dp.append(num[i])
            elif num[i] <= dp[0]:
                dp[0] = num[i]
            else:#dp[0] < num[i] <=dp[-1],二分查找
                low = 0
                high = len(dp)              
                while low < high:
                    mid = int((low + high) / 2)
                    if dp[mid] > num[i]:
                        high = mid
                    else:#dp[mid] < num[i]
                        low = mid + 1
                dp[low] = num[i]
        print(len(dp))
        print(dp)
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值