Seo tools

Neo Inspiration

  • Search

    • About Me

      • inspi 改め
        jakk@webアーキテクト(自称)
        php,javascript,seoなど
        得意技は extract();



  • Categories

  • Ranking

  • Comments

  • Others


    • track feed   |
  • mysql4.0系でfulltextを利用したマルチバイト全文検索2

    前回の続き

    とりあえず強引に mysql4.0系でマルチバイト対応全文検索してみるだけ。
    簡単に言えばトークンに切り出して、それをmd5して別テーブルに格納するという力ワザ。

    どうやってトークンを切りだすか

    以前流行った正規表現ベースのトークンとn-gramで速度比較

    100文字ほどのデータだと
    %php -f morph.php  ←正規表現ベース
    0.0232629776001sec
    %
    %php -f ngram.php ←tri-gram
    0.029877967834sec
    %
    
    10万文字ほどのデータだと
    %php -f morph.php ←正規表現ベース
    8.76749396324sec%
    %
    %php -f ngram.php ←tri-gram
    9.08151698112sec%
    

    あんまりかわらないのでワンライナーな正規表現ベースでやってみる。

    こんなかんじの正規表現。

    $r = preg_match_all('/[一-龠々〆ヵヶ]+|[ぁ-ん]+|[ァ-ヴ]+|[a-zA-Z0-9]+|[a-zA-Z0-9]+/u’, $str, $m);
     
    

    この正規表現で各レコードの本文を割って
    出てきたトークンを一つづつハッシュにしてjoinする

    $tempToken = array();
    foreach ($m as $v) {
        $hashedToken[] = md5($v);
    }
    $joinedToken = join(’ ‘,$hashedToken);
     
    

    でこれをトークン専用カラムを作成してそこに突っ込む。

    ここまでできたら
    検索クエリも上の正規表現でトークンにしてそれをmd5にしてから検索。

    テストしてみる
    全文中から 86deb27a32903da70a7b2348fcf36bc3(あいうえおのmd5) を検索
    
    SELECT id,MATCH (test_fulltext) AGAINST ('86deb27a32903da70a7b2348fcf36bc3')
    FROM **table
    WHERE MATCH (test_fulltext) AGAINST ('86deb27a32903da70a7b2348fcf36bc3')
    ORDER BY MATCH (test_fulltext) AGAINST ('86deb27a32903da70a7b2348fcf36bc3') ASC
    
    クエリの実行時間 0.0065 秒
     
    

    おーあたったあたった。
    しかもこれなら mysqld のft_min_word_lenを4からいじれないっていう件も
    強制32文字になるわけだから解決!

    ちょいと手間だし、トークンの数 * 32バイト分1レコードのデータが膨れ上がりますが
    (まあ全文字md5にしないで、マルチバイトのとこだけ切り出してるわけだから、
    そこだけエンコードしてしまえば結構減るかも)
    こういう方法で一応できるということで。

    っていうか pack() とか使えばもっと短くなるかな。


    Leave a Reply

    2009/01/07 10:44:58