最長遞增子串行(longest increasing subsequence,lis)指的是找到乙個特定的最長的子串行,並且子串行中的所有元素單調遞增。
例如, 的 lis 是 ,長度為 4
思想:
假設長度為n的陣列
假設陣列
初始化長度為n=6的陣列l,
表示以
結尾的最長遞增子序的長度,即
遍歷 計算
對於每個i, 需要遍歷 j ( 0< j < i)
如果 則
即 元素可以接到l[j]對應的lis的末尾,因此長度加1, max是為了保證l[i]永遠是最大值; 否則
得到陣列
獲取其中的最大值,則為最長遞增子串行的長度
時間複雜度 :
實現
def get_lis_length(arr):
"""動態規劃發獲取最長遞增子串行長度
:param arr:
:return:
"""# lis[i]表示以arr[i]結尾的lis長度
lis = np.ones(len(arr))
for i in range(1, len(arr)):
for j in range(i):
if arr[i] > arr[j]:
lis[i] = max(lis[j] + 1, lis[i])
return int(lis.max())
arr = [2, 1, 5, 3, 6, 4, 8, 9, 7]
print(get_lis_length(arr))
思想:原始陣列為a, 建立乙個輔助陣列b, 變數end用來記錄b陣列末尾元素的下標
遍歷a中的所有的元素 x = a[i]
遍歷結束之後,b的長度則為最長遞增子串行的長度
時間複雜度:
實現
def get_lis_length(arr):
"""二分法獲取最長遞增子串行長度
:param arr:
:return:
"""temp = [arr[0]]
end = 0
for i in range(1, len(arr)):
if arr[i] > temp[end]:
end += 1
else :
pos = binary_search(temp,0, len(temp), arr[i])
temp[pos] = arr[i]
return end + 1
def binary_search(arr, start, end, value):
l = start
r = end-1
while l <= r:
m = (l + r) //2
if arr[m] == value:
return m
elif arr[m] < value:
l = m + 1
else:
r = m - 1
return l
arr = [2, 1, 5, 3, 6, 4, 8, 9, 7]
print(get_lis_length(arr))
子串行1 最長遞增子串行
子串行問題本來就比子串和子陣列要難,因為子串行是不連續的,窮舉困難,而且子串行一般涉及兩個字串,一般來說都是讓求乙個最長子序列,涉及子串行和最值,那一定是動態規劃,o n2 1.定義dp陣列有兩種思路,第一種是乙個一維的dp陣列,兩次for迴圈來解決,dp i 的含義是在array陣列中,以arra...
動態規劃 最長連續遞增子串行的元素個數
例如 vector origin,因為最長連續遞增序列是 所以最長連續遞增子串行個數是5 思路都在 裡面 include include include include using namespace std 動態規劃 狀態定義 dp i 代表以a i 結尾的最長遞增子串行長度 狀態轉移 if a ...
最長公共子串行 最長遞增子串行 最長遞增公共子串行
求最長公共子串行 int dp maxn maxn int a maxn b maxn int main else dp i j max dp i 1 j dp i j 1 printf d n dp m n return 0 輸出最長公共子串行 int dp maxn maxn int d max...