2つのシーケンスが与えられた場合、それらに存在する可能性のある最長共通部分列をすべて出力します。

例えば、

Input:  X = XMJYAUZ, Y = MZJAWXU
Output: MJAU
 
 
Input:  X = ABCBDAB, Y = BDCABA
Output: BCAB, BCBA, BDAB

Practice this problem

の中に 前の投稿、最長共通部分列の長さを見つける方法について説明しました。この投稿では、最長共通部分列自体を印刷する方法について説明します。

 
させて X なれ XMJYAUZY なれ MZJAWXU。間の最長共通部分列 XYMJAU。次の表は、プレフィックス間の最長共通部分列の長さを示しています。 XY。 The i'th 行と j'th 列はLCSの部分文字列の長さを示します X[0…i-1]Y[0…j-1].

Longest Common subsequence

 
強調表示された数字は、LCSを読み取るときに右下から左上隅までたどるパスを示しています。現在の文字が XY 等しい(太字で示されている)、それらはLCSの一部であり、斜めに移動します。現在の文字が XY 異なる場合は、どちらのセルの数が多いかに応じて、上または左に移動します。これは、LCSを X[0…i-2], Y[0…j-1]、 また X[0…i-1], Y[0…j-2].

 
次のC++、Java、およびPythonの実装は、ルックアップテーブルを ボトムアップ方式 次に、LCSを再帰的にに検索します トップダウン ルックアップテーブルの値を使用する方法。

C++


ダウンロード  コードを実行する

出力:

MJAU

Java


ダウンロード  コードを実行する

出力:

MJAU

Python


ダウンロード  コードを実行する

出力:

MJAU

可能なすべてのLCSを出力するようにコードを変更するにはどうすればよいですか?

上記のコードは、指定されたシーケンスの最長共通部分列をすべて生成するわけではありません。常に1つのLCSを印刷します。上記のコードの問題は、 XY 異なる場合は、の最後の文字のいずれかを破棄します X またはの最後の文字 Y 現在のセルに対する上部または左側のセルの値に基づきます。しかし、LCSが破棄された文字でも可能である場合はどうなりますか?

上のセルが左のセルと等しい場合を除いて、考え方は同じです。両方の文字を考慮してください。それ以外の場合は、より大きな価値の方向に進みます。アルゴリズムは、C++、Java、およびPythonで次のように実装できます。

C++


ダウンロード  コードを実行する

出力:

BCAB
BCBA
BDAB

Java


ダウンロード  コードを実行する

出力:

[BCAB, BCBA, BDAB]

Python


ダウンロード  コードを実行する

出力:

{‘BCBA’, ‘BDAB’, ‘BCAB’}

参照: https://en.wikipedia.org/wiki/Longest_common_subsequence_problem