最長上公升子串行 LIS

2021-07-11 21:47:06 字數 1588 閱讀 3853

題目:

兩道題幾乎一樣,只不過對於輸入輸出的要求有所不同罷了。

lis有兩種方法:

一、第一種方法 · 時間複雜度為o(n^2):

狀態:dp[i] := 區間為0~i的序列的lis

轉移方程:dp[i] = max(1, dp[k] + 1)  (0<=k

#include #include 

#include

#include

using

namespace

std;

char s[10005

];int dp[10005

];int

main ()}}

int ans = 0

;

for(int i=0; imax(ans, dp[i]);

printf(

"%d\n

", ans);

}return0;

}

這種方法需要用二分查詢查詢到當前這一位元素應該是長度為多少的上公升子串行的最後一位。

狀態定義:dp[i] := 長度為i的上公升子串行的當前最小的末尾元素,這裡之所以要找最小的末尾元素,是因為越小越容易在後面加上乙個稍大的元素使得找到的lis更長!換句話說,倘若我已經將末尾元素的值設定為最低,盡力減小後來者的「門檻」了,但長度仍然只有這麼多,那麼上公升子串行的最長長度也就只能是這樣了。

舉個例子:序列s為

step1:將陣列dp初始化為

step2:開始遍歷序列s

① 當前遍歷到的元素為1時,我們在dp序列進行二分查詢,尋找第乙個大於等於1的元素的下標,我們找到dp[1]=+∞是第乙個大於1的元素(dp的下標從1開始),於是dp[1]=1,即:目前來看,長度為1的上公升子串行的末尾元素為1

② 當前遍歷到的元素為4時,在dp序列中找到第乙個大於等於4的元素為dp[2]=+∞,所以dp[2]=4。這時,dp=,說明長度為1和2的上公升子串行的最小末尾元素都已經找到。

③ 當前遍歷到的元素為2時,在dp序列中找到第乙個大於等於2的元素為dp[2]=4,這說明元素2沒有辦法讓目前的最長上公升序列更長(除非》4),但是相對於它後面的元素而言,它更有「潛質」作為長度為2的上公升子串行的末尾元素,因為它比當前的4要小,4能做到的它都可以,而且可能得到比4更長的上公升序列,即做得還可能比4要好。

#include #include 

#include

#include

#include

#define inf 30

using

namespace

std;

char s[10005

];int dp[10005

];int

main ()

for(int i=0; i)

printf(

"%d\n

", lower_bound(dp, dp+len, inf) -dp);

}return0;

}

最長上公升子串行LIS

問題 給定n個整數a1,a2,a3,a4,a5,an,從左到右的順序盡量選出多個整數,組成乙個上公升子串行,相鄰元素不相等。例如 1,6,2,3,7,5,它的最長上公升子串行為 1,2,3,5。分析 剛開始想這個問題的時候我想用遞迴來解決問題,可是後來考慮到遞迴的時間複雜度高,就覺得不能使用,並且本...

LIS 最長上公升子串行

最長遞增子串行問題 在一列數中尋找一些數,這些數滿足 任意兩個數a i 和a j 若i 設dp i 表示以i為結尾的最長遞增子串行的長度,則狀態轉移方程為 dp i max,1 j 這樣簡單的複雜度為o n 2 其實還有更好的方法。考慮兩個數a x 和a y x 按dp t k來分類,只需保留dp ...

最長上公升子串行(LIS)

問題 有乙個長為n的數列,a1,a2,an 1。請求出這個序列中最長的上公升子串行的長度。上公升子串行指的是對於任意的i j都滿足ai aj的子串行。dp i 以a i 結尾的最長上公升子串行的長度 時間複雜為o n 2 for int i 0 i1 for int j 0 jif a j max ...