示例: 輸入: [10,9,2,5,3,7,101,18] 輸出: 4 解釋: 最長的上升子序列是 [2,3,7,101],它的長度是 4.
class Solution: def lengthOfLIS(self, nums) -> int: length = len(nums) new_arr = [] # 最長上升子列數組 if length == 0: # 原數組爲空 return 0 elif length == 1: # 原數組只有一個元素 return 1 else: new_arr.append(nums[0]) for i in range(1, length): if nums[i] <= new_arr[0]: # 若是遍歷的元素比子列中最小值還小或相等,則替換 new_arr[0] = nums[i] elif (new_arr[0] < nums[i]) and (nums[i] <= new_arr[-1]): # 若是遍歷的元素值大小在子列中間,則查找到第一個大於或等於此元素的子列元素,進行替換;new_arr目前是已經有序的,因此能夠用二分查找提升檢索效率 low,high = 0,len(new_arr)-1 while low <= high: mid = (low+high)//2 if new_arr[mid] >= nums[i]: new_arr[mid] = nums[i] break else: low = mid + 1 elif nums[i] > new_arr[-1]: # 若是遍歷的元素比子列最大元素還大,則追加到子列尾部 new_arr.append(nums[i]) return len(new_arr)
執行用時 : 52 ms, 在Longest Increasing Subsequence的Python3提交中擊敗了96.97% 的用戶 內存消耗 : 13.1 MB, 在Longest Increasing Subsequence的Python3提交中擊敗了96.54% 的用戶java
import java.util.ArrayList; import java.util.Scanner; import java.util.List; public class SubSequence { public static void main(String[] args) { Scanner sc = new Scanner(System.in); int n = sc.nextInt(); int[] s = new int[n]; for(int i=0; i<n; i++){ s[i] = sc.nextInt(); } int max_len = getSubSequenceLen(n, s); System.out.println("最長遞增子序列長度:"+max_len); } public static int getSubSequenceLen(int n, int[] s){ int[] liss = new int[n]; // 以各元素結尾的最長遞增子序列長度 int[] pre = new int[n]; // 以各元素結尾的最長遞增子序列的當前元素的前向元素 List<Integer> maxSubSequence = new ArrayList<Integer>(); int max_len = 1; // 最長遞增子序列長度 int end_index = 0; // 長遞增子序列尾元素地址 // 初始化 for(int i=0; i<n; i++){ liss[i] = 1; pre[i] = s[i]; } for(int p=1; p<n; p++){ for(int q=0; q<p; q++){ if(s[q]<s[p] && liss[q]+1>liss[p]){ liss[p] = liss[q]+1; pre[p] = s[q]; end_index = p; } } if(max_len<liss[p]){ max_len = liss[p]; maxSubSequence.add(pre[p]); // 將最長遞增子序列中當前元素的前向元素添加進來 } } maxSubSequence.add(s[end_index]); // 將最長遞增子序列的尾元素添加進來 System.out.println("最長遞增子序列:"+maxSubSequence); return max_len; } }