web-dev-qa-db-ja.com

2つの大きな文字列を比較して、それらがどの程度一致しているかを確認する

2つの異なるサイズの文字列テキストを比較して、どれくらいの割合で似ているかを確認する簡単な方法はありますか?

私はこれを試していますが、以下のこの問題が発生しています。左側のテキスト領域は、コピーするテキストです。右は、テキストをコピーしようとしているユーザーです(この例では、ユーザーはすべてが正しく入力されず、スペルミスの単語やユーザーが入力し忘れた単語があります)。 enter image description here

カウントダウンの期限が切れた後、ユーザーが指定されたテキストを左側に正しくコピーした割合を計算します。左下の左上にあるテキストボックスのテキストを、テキストフィールドでsplit( "")コマンドを使用して配列に配置しています。右下は、ユーザーが入力したテキストについても同じです。 enter image description here

ユーザーが正しく入力したパーセンテージを計算する前に、以下のコードが示すように、ユーザーが正しく入力した単語の数を合計してみます。

for(var counter = 0; counter < userArr.length; counter++)
{
    if(userArr[counter] === textArr[counter])
    {
        correct++;
    }
}

配列のインデックス3で、ユーザーは問題のないものを誤って入力しました。しかし、インデックス6では、ユーザーは単語の入力を完全に逃しました。そのため、残りのインデックスが少なくとも1つずれて、正しく入力された単語の量が取得されます。それがなければ、私は正しくタイプされたパーセンテージを計算することができません。

私には、それを説明するためにforループ内に一連の条件付きチェックを作成する必要があるようです。しかし、少し厄介なようです。

だから私の元の質問に戻って、ifステートメントの大きな混乱を作成せずにこの計算を行う簡単な方法はありますか?つまり、オープンソースのメソッド、またはこれを処理するための組み込みのJavaScriptメソッドはありますか?

6
CAM_344

既存のライブラリ関数(Linuxコマンドラインユーティリティdiff、T-SQL Word NEAR、またはPHP function array_intersect())を使用すると、独自のアルゴリズムを開発できます。また、さまざまなバリエーションが可能です...ただし、複雑なものもあります。ここで私が思いついた1つのソリューションの大まかなドラフトです。 O(log(n))の時間の複雑さ(これは、ループ内でのループの量が減少することを意味し、特に高速ではありません)。

  1. 上記の作者が行ったように、文字列内の単語を空白やその他の句読点に基づいて配列要素に分割します。
  2. 最初の配列の反復を開始します。
  3. その最初の要素を2番目の配列の最初の要素と比較します。
  4. 要素が一致する場合は、ポインタを上げ(2番目から2番目など)、連続する一致が見つかる限りこれを続けます。
  5. 不一致に到達したら、一連の連続する一致(「共通セクション」と呼びます)の開始点と終了点を別の配列に格納します。たとえば、1番目の配列の要素4〜12は、2番目の配列の要素7〜15と一致する場合があります。
  6. 不一致の最初のインスタンスで、ポインターをリセットし、「共通セクション」にまだ含まれていないポイントで配列を繰り返すことに戻ります。そして、「カバーされている」とすでにマークされているものをスキップします(いずれか)サブエレメントでフラグが付けられているか、既存の「共通セクション」のいずれかの範囲でカバーされている)。
  7. 配列の反復が完了したら、最も長いものやカバレッジエリアが最大になるものを優先して、順序の乱れた「共通セクション」を「もつれ」ます。
  8. 「共通セクション」の最後のセットによって一致する要素と一致しない要素を数え、カバーされる割合を計算します。
2
John Doe

私はあなたが探していると信じています Edit Distance これは、2つの単語の近さを分析する数値的な方法を提供します。もちろん、これは完全な文に外挿できます。

2
James

編集距離 のさまざまな形式の1つを探しています。編集距離の正式な定義は次のとおりです。

2つの文字列abがアルファベットΣで与えられた場合(ASCII文字のセット、バイトのセット[0..255]、CTAGなど)、編集距離d(ab)は、ab

これから、26または28の文字列はなく、one文字列になります。これは大きな問題ですが、全体を見るとわかります。

さまざまな変換とアルファベットに焦点を当てた編集距離には多くのタイプがあります。たとえば、 Levenshtein distance は、任意の文字列の挿入、削除、および置換の変換で機能します。ここで、 Hamming distance は、2つの文字列が異なる場所の数です。 Damerau–Levenshtein distance は、2つの隣接する文字の転置をレーベンシュタイン距離に追加します(つまり、hteからtheは2ではなく1の距離になります)。スペルチェックとDNAのバリエーションには、より便利です(ただし、 Needleman–Wunschアルゴリズム は、DNAの文字列に適しています)。

0
user40980