[Senna-dev 618] Re: 複数カラムに対するOR検索時のパフォーマンス悪化について

Back to archive index

Yuki Horikoshi horik****@maste*****
2007年 6月 25日 (月) 21:36:01 JST


末永様

適切・迅速なご回答ありがとうございます。
内容についても大変わかりやすく、とても参考になりました。

今回は
> CREATE TABLE TAB1 (COL1 TEXT, COL2 TEXT, FULLTEXT(COL1, COL2));
にて高速な結果取得が可能になりました。

> SELECT * FROM TAB1 FORCE INDEX (PRIMARY)
>  WHERE MATCH(COL1) AGAINST ('検索語') OR
>        MATCH(COL2) AGAINST ('検索語');
こちらも若干の速度改善(10%程度)が見られましたが、
like検索よりは時間がかかってしまうようでした。

取り急ぎ、インデックス形式の変更にて期待通りの結果が出ました。
本当にありがとうございました。

> 未来検索ブラジルの末永です。
> 複数カラムを対象としたOR検索が遅い件についてです。
> 
> ●解決方法1
> 
> まず、TAB1の定義を以下のように変更します。
> CREATE TABLE TAB1 (COL1 TEXT, COL2 TEXT, FULLTEXT(COL1, COL2));
> 
> そして、
> SELECT * FROM TAB1 WHERE MATCH(COL1, COL2) AGAINST('検索語');
> を実行すると所望の結果が得られます。
> 
> 現在のTritonnの実装では、複数のカラムに対してインデックスを作成した場合、
> SELECT CONCAT(COL2, " ", COL1) AS COL FROM TAB1;
> で取得できる値COLをインデックスの対象にします。
> (インデックス定義時のカラムの順番に対して逆順で連結しています)
> 
> よって、COL1とCOL2に対してインデックスを作成して、
> それに対して検索をかけることで、
> COL1またはCOL2に検索単語が存在するレコードが取得できます。
> 
> ●解決方法2
> UNIONで高速ということであれば、
> もしかしたら以下のクエリで速度が上がる可能性があります。
> 
> SELECT * FROM TAB1 FORCE INDEX (PRIMARY)
>  WHERE MATCH(COL1) AGAINST ('検索語') OR
>        MATCH(COL2) AGAINST ('検索語');
> 
> なお、この場合はSennaが2回呼ばれてしまうので、
> 解決方法1よりも速度が劣ると思います。
> 
> ●メモ
> 一般的にOR検索は検索結果が増えてしまうので、
> 処理速度が遅くなる傾向にあります。
> 
> たとえば、
> SELECT * FROM TAB1
>  WHERE MATCH(COL1) AGAINST('未来 検索' IN BOOLEAN MODE);
>> SELECT * FROM TAB1
>  WHERE MATCH(COL1) AGAINST('*D+未来 検索' IN BOOLEAN MODE);
> では後者のほうが速く検索することができます。

---
Yuki Horikoshi <horik****@maste*****>




Senna-dev メーリングリストの案内
Back to archive index