• 締切済み

テキストの中から与えられた文字を含む最短の文字列を求める為のアルゴリズムについて

例)Thatisanotebook. というテキストがあったとします。 与えられた文字がost(順番は構わない)だとすると、ostを含む最短の文字列はsanotです。 このときsanotと導くためのアルゴリズムが分かりません。 for文を使った簡単なものは作れるのですが、処理が遅すぎて困っています。 どなたかご教授お願いします。

みんなの回答

  • yama5140
  • ベストアンサー率54% (136/250)
回答No.2

★解答( sanot )の頭は、検索文字( o, s, t )である。  このことから、対象となる文字列 Thatisanotebook  の頭から、検索文字( o, s, t )以外を除外していく(◆)。 ★残った文字列( tisanotebook )から、検索文字( o, s )の内、  最後に検索した場所(▲最後-トップ)を、メモしておく(●)。  (1つの解答が得られた) ★次に、◆と同様に、検索文字( o, s, t )以外を除外し、  残った文字列( sanotebook )から、・・(略:繰り返し) てのは如何でしょう。 >for文を使った簡単なものは作れるのですが、処理が遅すぎて困っています。  「丸投げ」ではないので、「瞬時」に結果の出るソースを・・。 ★参考になればよいのですが(ずいぶん長くて・・申し訳ない) ----------------------------------------------------- #include <stdio.h> #include <string.h> typedef struct{  int iLen;  char cAns[32]; }MEMO; MEMO sWork[10]; int UseTotal( int iUse[] ) {  int i, iTotal = 0;  for( i = 0; i < 8; i++ ) iTotal += iUse[i];  return( iTotal ); } void main() {  char cTaisyou[32] = "Thatisanotebook";  char cKensaku[ 8] = "ost";  int i, j, iLen, iTop, iHead;  int iUse[8], iKenCnt = 0, iMojiSu;  iMojiSu = strlen( cKensaku ); // 検索文字数  for( iTop = 0; iTop < 32; iTop++ ){   if( 0x00 == cTaisyou[iTop] ) break;   iHead = 0;   for( i = 0; i < iMojiSu; i++ ){    if( cKensaku[i] == cTaisyou[iTop] ){     iHead = 1;     break;    }   }   if( 0 == iHead ) continue; // ◆   for( i = 0; i < 8; i++ ) iUse[i] = 0; // 初期化   for( j = iTop; j < 32; j++ ){ // 対象文字列を1つずつ    if( 0x00 == cTaisyou[j] ) break;    for( i = 0; i < iMojiSu; i++ ){     if( iUse[i] ) continue;     if( cKensaku[i] == cTaisyou[j] ){      iUse[i]++; // 検索文字使用済み      if( UseTotal( iUse ) == iMojiSu ){ // ●       iLen = j - iTop + 1; // ▲       strcpy( sWork[iKenCnt].cAns, &cTaisyou[iTop] );       sWork[iKenCnt].cAns[iLen] = 0x00;       sWork[iKenCnt].iLen = iLen;       iKenCnt++;      }      break;     }    }   }  }  for( i = 0; i < iKenCnt; i++ ){ // ●出力   printf( "%2d %s\n", sWork[i].iLen, sWork[i].cAns );  } } 注:インデントに全角空白を用いています。   タブに一括変換して下さい。

  • koko_u_
  • ベストアンサー率18% (459/2509)
回答No.1

>for文を使った簡単なものは作れるのですが、処理が遅すぎて困っています。 じゃあ、まずはそのソースを補足にどうぞ。

関連するQ&A

  • 文字列の検索アルゴリズム

    「私は世界一頭がいいので、数学なんか簡単すぎていいかげん飽きてきた。」 この文字列から「いいかげん」を検索するアルゴリズムにはどんなものがあるのでしょうか? 条件 ・100KB(5万字)程度のデータから10文字程度指定文字列を検索する。 ・100KBと元データもそれほど大きくないので、プログラムが簡単なアルゴリズムが良い。 ・そのアルゴリズムの解説がインターネット上にあること。 単純に「い」を探して合致したら次の文字も「い」であることを確認。 さらに次の文字が「か」であることを確認。 さらに・・・「げ」・・「ん」 とやっていく方法でも良いとは思うのですが、もしかしたらもっとお手軽かつ高速にできる方法があるのかなと思い質問してみました。 なければないという回答でもかまいません。 また、参考までにテキストエディタ等がどのようなアルゴリズムを用いているのか知っている方(推測できる方)はその方法についても教えて頂ければと思います。 よろしくお願いします。

  • 文字列の探索アルゴリズムについて

    松井勝正といいます。自分なりのアイディアで文字列の探索アルゴリズム を作成したのですが。質問が2点程あります。 1点目:既に世に出回っているアルゴリズムかご教授願えれば幸いです。 2点目:改良の余地やバグ等ございましたらご指摘いただければ幸いです。 それではよろしくお願いいたします。

  • javaScriptで、テキストエリアのある文字列を見つけて、

    javaScriptで、テキストエリアのある文字列を見つけて、 その行から、1行目と2行目を消すという処理を行いたいのですが、 コーディングがわかりません。 教えて下さい。 (例) 下記のテキストエリアから、「<ターゲット文字列>」を見つけて、 その行から1行目と2行目、つまりは、「さしすせそ」と「たちつてと」を削除したいです。 -----textarea----- あいうえお かきくけこ <ターゲット文字列> さしすせそ たちつてと

  • 文字列中からある文字列とある文字列の間にある文字列を取得

    表題にあるとおり間の文字列をどうやって取得するべきかと悩んでいます・・ abcdefghijklmn・・・ となっているとき bとe、aとkなど間の間隔が不定なときはどのようにして文字列を取得したらよいのでしょうか? 最初の2文字は与えられているとして考えています。 インターネットのURLで言うなら/から/までの間の文字列と言うことになります。 今私が考えているのは strchrで位置のアドレスを取得してそこからfor文かwhile文で指定の2文字目が出るまでまわすのかなぁ・・と思っています。 ですが具体的にどのような感じに書けばいいのかがわかりません。どなたかご教授ください。

  • $textの文字列の中にある & を ■ に変えたいです。

    <? $text ="u&ampampfayv&ampin&ampe6&rna6uinv"; ///////////////////////////// print $text."<br>"; print "<XMP>".$text."</XMP><br>"; ///////////////////////////////正規表現で置換 $text = preg_replace('/&[^amp]/', "■", $text); ////////////////////////////// print $text."<br>"; print "<XMP>".$text."</XMP><br>"; ////////////////////////////// print "u&ampampfayv&ampin&ampe6■rna6uinv"; print "<XMP>u&ampampfayv&ampin&ampe6■rna6uinv</XMP>"; ?> $textの文字列の中にある & を ■ に変えたいです。 amp という文字列の前についている & は ■ に置換してはいけません。 &ampamp という文字列の前についている & も ■ に置換してはいけません。 現在の正規表現では r が消えてしまっています。 ブラウザで見た場合に結果が u&ampfayv&in&e6■rna6uinv になるようにして下さい。 よろしくお願いします。

    • ベストアンサー
    • PHP
  • エクセルファイルから指定列の文字を

    エクセルファイルから指定列の文字を、別のテキストファイルの特定の場所へ順番に差し替えたいです。 【例】 A列の文字→元からあるテキストファイルの内容そのままに、●という特定文字へ、住所1、住所2、住所3・・・ というようにエクセルの列に従って、順番に差し替えてくれる方法ってあるでしょうか? コピペだと大変です(涙) よろしくお願いします。

  • 配列の中に重複文字列があるか否かをチェックしたいのですが、アルゴリズムを教えてください。

    配列10000個の中に次のように文字列が入っているとします。 (実際に使うのはもっとずっと長い文字列が配列内に格納されています。) Data_Array[1] = "GRZRMZCOMKMSG" Data_Array[2] = "DCUIROTLUMWBC" Data_Array[3] = "RGLBMILRPBSMY" . . . Data_Array[9998] = "RSKFDHAHMOESI" Data_Array[9999] = "AQVOXBVNILGOP" Data_Array[10000] = "YNYRUPEXYOGFN" 配列Data_Array[10000]の中に重複文字列がないか探索したいと考えています。 ~普段の手順~ 配列中身を一度テキストに吐き出し、そのテキストをExcelに貼り付ける。 そして、Excelのフィルタ機能で重複文字列を排除。 その後、重複文字列を排除した文字列を保存したものをテキストファイルに保存する。 それをプログラムで読み込んで配列内に格納してから次の処理を続ける といった、効率の悪い方法をとっています。 そこで、プログラム内で処理する方法を次のように考えてみました。 ~思いつく方法~ dim DataArrayTemp[10000] for i = 1 to 10000 flag = 0 // 重複文字がないかチェック for j = i+1 to 10000 ifb Data_Array[i] = Data_Array[j] then // 重複があった場合はflag = 1にする flag = 1 break // 内ループ脱出 endif next // flag = 0であれば重複がない項目 (flag = 1のときは、重複がある) ifb flag = 0 then DataArrayTemp[temp_i] = Data_Array[i] temp_i = temp_i + 1 endif next これは、力技なので配列内の量が多くなると計算時間がかかってしまいます。 ですので、重複しない文字列だけを抽出する効率の良い方法がありましたらどなたか知恵を貸してください。

  • 文字列の圧縮・復元アルゴリズムで困っています

    昔専門学校でやったけれど完全に忘れてしまっている文字列圧縮・復元の アルゴリズムについて教えて頂きたいのです。 仕様としては文字列「AAAABBBCCDDDDDEF」と並んでいた場合に圧縮を 実行すると「A4B3C2D5EF」と文字列を圧縮し、復元の場合はこの文字列を元に 圧縮前の文字列「AAAABBBCCDDDDDEF」にするといった感じのものです。 C言語かC#言語で答えて頂けるとありがたいです。

  • 文字列探索アルゴリズム(Aho Corasick法)をC言語で組みたい

    はじめまして。 標題のとおり、 文字列探索アルゴリズム(Aho Corasick法)をC言語で組みたいと考えています。 簡単なコード例か、どこか情報元はありませんでしょうか? 文字列「あかさたなはまやらわ」から キーワード「あか」・「たな」を探して 出力として、 「あか」…インデックス0 「たな」…インデックス3 となるようなイメージのプログラミングです。 詳しい方がおりましたら、何卒ご教授お願い致します。

  • 文字列をテキストフィールドに差し替える方法

    こんばんは。 以下のような処理をJavaScriptで実現したいと思っているのですが、 うまく出来ません。 1.HTMLファイル上に「あいうえお」という文字列があったとする。 2.文字列のとなりのボタンを押すと、「あいうえお」があった場所がテキストフィールドになって、 「あいうえお」という文字が入力済みで編集可能になる。 3.もう一度ボタンを押すと、テキストフィールドが元通りの普通も文字列に戻る。 以前、どこかのサイトでこのような動きを見たので、 簡単に出来るのかな、と思っていたのですが、、、 お詳しい方がいらっしゃいましたら、知恵を貸していただけないでしょうか?? 宜しくおねがいします。

専門家に質問してみよう