2012-04-01 9 views
2

サブシーケンスの前半が後半と同じように最長サブシーケンスを探したいとします。文字列中で最長類似サブシーケンスを見つける

例:abkcjadfbckという文字列の場合、abcabcは最初と後半で繰り返されるため、結果はabcabcとなります。攪拌中に結果はaaです。

+0

私はそれを取得しません。最初の文字列のどこに 'abc'がありますか?なぜ2番目の文字列の結果は 'aaa 'ではないのですか?明らかにそれはもっと長い。 –

+1

サブシーケンスは、インデックスが連続していなければならないとは限りません。結果のaaは[index 0、index 1]、[index 1、index 2]、または[index 0、index 2]のいずれかです。 – DaveFar

+0

aaaには "aa"という結果があります。これは、 "aa"では前半が後半と同じであるためです。 – test

答えて

1

このタスクは、2つのよく知られた問題の組み合わせとして扱われます。

  1. サブシーケンスの2つの半分の間にある点が事前に分かっている場合は、2つの文字列の最適な一致を見つける必要があります。これはPairwise alignment問題です。様々な動的プログラミング方法がO(N )時間でそれを解決します。
  2. 文字列を最適に分割するポイントを見つけるには、Golden section searchまたはフィボナッチ検索を使用できます。これらのアルゴリズムは、O(log N)時間の複雑さを有する。
+0

それで、私がurメソッドから理解していることは、.. i = 1:nから、2つの文字列を作成し、それらの上に最も長い共通部分シーケンスを実行するだけです。したがって、同様の半分の最長部分列を見つけるためにn *(n * n)の順序になります。しかし、可能なすべての文字列を生成することはできますか?たとえば、aaaの場合、aa、aa、aaの3つの文字列を使用できます。 (最初の "a"、最初の "a"と3番目の "a"、2番目の "a"と3番目の "a") – test

+0

これらのアルゴリズムで最も長い部分シーケンスを検索すると、Oゴールデンセクションの検索では、すべての可能な位置で文字列を分割する必要はありません。しかし、これはすべての部分列を得ることを許さない。すべての部分列を生成することは全く別の作業であり、他の方法で対処する必要があります。 –

0

inputStringの最初のパスでは、各文字がどのくらいの頻度で出現するかをカウントし、出現1のものを削除できます。

input: inputString 
data strucutres: 
Set<Triple<char[], Integer, Integer>> potentialSecondWords; 
Map<Char, List<Integer>> lettersList; 

for the characters c with increasing index h in inputString do 
    if (!lettersList.get(c).isEmpty()) { 
    for ((secondWord, currentIndex, maxIndex) in potentialSecondWords) { 
     if (there exists a j in lettersList.get(c) between currentIndex and maxIndex) { 
     update (secondWord, currentIndex, maxIndex) by adding c to secondWord and replacing currentIndex with j; 
     } 
    } 
    if potentialSecondWords contains a triple whose char[] is equal to c, remove it; 
    put new Triple with value (c,lettersList.get(c).get(0), h-1) into potentialSecondWords; 
    } 
    lettersList.get(c).add(h); 
} 
find the largest secondWord in potentialSecondWords and output secondWord twice; 

したがって、このアルゴリズムは、それが理にかなって各インデックス、現在のインデックスから始まる電位第2のワードを表すトリプルための作成、アレイの上に一度通過し、すべての潜在的な第二の単語を更新します。

適切なリストの実装では、nはinputStringのサイズであり、このアルゴリズムは最悪の場合ランタイムO(n²)を持ちます。^nのために。

+0

あなたはアルゴについて説明できますか? – test

関連する問題