最長公共子串行 最長連續公共子串行 最長遞增子串行

2021-08-18 05:20:29 字數 3405 閱讀 4253

面試中除了排序問題,還會經常出現字串的子串行問題,這裡講解使用動態規劃解決三個常見的子串行問題:

1、最長公共子串行問題(lcs,longest-common-subsequence problem)

2、最長連續公共子串行問題

3、最長遞增子串行(lis,longest-increment-subsequence)

給定兩個序列x=

,x2,

...,

xmx 1,

x2,.

..,x

m>和y=

,y2,

...,

yny 1,

y2,.

..,y

n>,求x和y的最長公共子串行。(子串行可以是不連續的,比如就是的子串行)

例如:輸入兩個字串 bdcaba 和 abcbdab,字串 bcba 和 bdab 都是是它們的最長公共子串行,則輸出它們的長度 4,並列印任意乙個子串行。

時間複雜度o(m*n),空間複雜度o(m*n)。

在使用動態規劃之前先規定一下符號,給定乙個序列x=

,x2,

...,

xmx 1,

x2,.

..,x

m>,定義xi

x

i為x的字首,即xi

x i=

,x2,

...,

xix 1,

x2,.

..,x

i>。

在求x=

,x2,

...,

xmx 1,

x2,.

..,x

m>和y=

,y2,

...,

yny 1,

y2,.

..,y

n>的乙個lcs時,我們需要求解乙個或者兩個子問題。如果xm

=yn xm=

yn,那麼我們應該求解xm

−1=y

n−1 xm−

1=yn

−1的乙個lcs。如果xm

≠yn xm≠

yn,我們必須求解兩個子問題:求xm

−1x m−

1和y y

的乙個lcs與

x' role="presentation" style="position: relative;">xx和

yn−1

y n−

1的乙個lcs。兩個lcs中較長的乙個,即為x和y的乙個lcs,經過推理可知,這些子情況覆蓋了所有可能出現的情況。

所以遞推公式為:

具體到實際的例子中:

// 列印c陣列

for(int i=0;i<=x.length;i++)

system.out.println();

}return c;

}// 輸出lcs序列

public

static

void

print(int arr, char x, char y, int i, int j) else

if(arr[i-1][j] >= arr[i][j-1]) else

}public

static

void

main(string args) ;

char y =;

int c = lengthoflcs(x,y);

print(c, x, y, x.length, y.length);

}}給定兩個序列x=

,x2,

...,

xmx 1,

x2,.

..,x

m>和y=

,y2,

...,

yny 1,

y2,.

..,y

n>,求x和y的最長公共公共子串行。(連續子串行必須連續的)

例如:輸入兩個字串 acbac和 acaccbabb,則最大連續子串為 「cba」, 則返回長度 3。

時間複雜度o(m*n),空間複雜度o(m*n)。

這個 lcs 跟前面說的最長公共子串行的 lcs 不一樣,不過也算是 lcs 的乙個變體,在 lcs 中,子串行是不必要求連續的,而子串則是 「連續」 的。

我們還是像之前一樣 「從後向前」 考慮是否能分解這個問題,類似最長公共子串行的分析,這裡,我們使用c[i,j] 表示 以 xi 和 yj 結尾的最長公共子串的長度,因為要求子串連續,所以對於 xi 與 yj 來講,它們要麼與之前的公共子串構成新的公共子串;要麼就是不構成公共子串。故狀態轉移方程:

}給定乙個序列x=

,x2,

...,

xmx 1,

x2,.

..,x

m>,求x的最長遞增子串行。(子串行可以是不連續的,比如 的lis是5,6,7,8

時間複雜度o(n^2),空間複雜度o(n)。

dp[i]怎麼計算?

遍歷所有j < i的元素,檢查是否dp[j]+1>dp[i] && arr[j] < arry[i] 若是,則可以更新dp[i]

以 的lis是5,6,7,8舉例:

如何選取dp[5]的值呢?就是在所有8之前的小於8的值(即j < i && arr[j] < arry[i])中,選擇dp[j]最大的值,

dp[i] = dp[j] + 1

dp[5] = dp[2] + 1 = 3 + 1 = 4

int maxlength = 1, bestend = 0;
dp[0] = 1;

prev[0] = -1;

for (int i = 1; i < n; i++)

if (dp[i] > maxlength)

最長公共連續子串和最長連續公共子串行

用二維陣列c i j 記錄串x1 x2 x i x1x2 xi與y 1y 2 y j y1y2 yj 的lcs長度,則可得到狀態轉移方程c i,j 0c i 1 j 1 1max c i,j 1 c i 1,j i 0 orj 0i,j 0a ndxi y j i,j 0a ndxi y j pub...

最長公共子串行 最長公共子串

1 最長公共子串行 採用動態規劃的思想,用乙個陣列dp i j 記錄a字串中i 1位置到b字串中j 1位置的最長公共子串行,若a i 1 b j 1 那麼dp i j dp i 1 j 1 1,若不相同,那麼dp i j 就是dp i 1 j 和dp i j 1 中的較大者。class lcs el...

最長公共子串行 最長公共子串

1.區別 找兩個字串的最長公共子串,這個子串要求在原字串中是連續的。而最長公共子串行則並不要求連續。2 最長公共子串 其實這是乙個序貫決策問題,可以用動態規劃來求解。我們採用乙個二維矩陣來記錄中間的結果。這個二維矩陣怎麼構造呢?直接舉個例子吧 bab 和 caba 當然我們現在一眼就可以看出來最長公...