SQL:前方一致・後方一致・部分一致検索する方法

SQLで前方一致・後方一致・部分一致等のあいまい検索の方法についてご紹介します。
SQLであいまい検索を行う場合はワイルドカード文字として「%」を使用します。

サンプルテーブル

以下の商品テーブル「goods」を元に説明します。

    商品テーブル「goods」
    //write-remember.com/wordpress/wp-content/uploads/2016/02/b8f86f58054e38e75bb14b5d465b829c.png\">//write-remember.com/wordpress/wp-content/uploads/2016/02/b8f86f58054e38e75bb14b5d465b829c.png\" alt=\"\" width=\"333\" height=\"176\" class=\"aligncenter size-full wp-image-4895\" />"

前方一致検索

SQL文(クエリー)

    • 前方一致検索する場合、LIKE演算子を指定して検索条件の最後に「%」を記載します。
    • 「SELECT * FROM [テーブル名] WHERE LIKE ‘[条件]%’;」の形式で記述します。

実行結果

以下の様に前方に「商品」と入力されているデータのみ出力されます。

後方一致検索

SQL文(クエリー)

    • 後方一致検索する場合、LIKE演算子を指定して検索条件の先頭に「%」を記載します。
    • 「SELECT * FROM [テーブル名] WHERE LIKE ‘%[条件]’;」の形式で記述します。

実行結果

以下の様に後方に「A」と入力されているデータのみ出力されます。

部分一致検索

SQL文(クエリー)

    • 部分一致検索する場合、LIKE演算子を指定して検索条件の前後に「%」を記載します。
    • 「SELECT * FROM [テーブル名] WHERE LIKE ‘%[条件]%’;」の形式で記述します。

実行結果

以下の様に文字列に「ボード」が含まれているデータが出力されます。

補足:実務で気をつけたいポイント & 応用例

1. ワイルドカード検索とインデックスの相性

LIKE 演算子を使ったあいまい検索は、通常のインデックスが利かないケースが多く、パフォーマンス低下の原因になります。

  • 前方一致('文字列%')であれば B-Tree インデックスが使われることもありますが、後方一致('%文字列')や部分一致('%文字列%')では使われないことが多いです。

  • 大量データを扱う場合は、全文検索エンジン(たとえば PostgreSQL の pg_trgm 拡張、Elasticsearch、MySQL の全文検索機能など)の導入を検討したほうがよいでしょう。

2. 大文字・小文字の扱い

データベースによっては、LIKE は大文字・小文字を区別するかどうかが異なります。

  • MySQL(latin1utf8_general_ci など)では大文字・小文字を区別しないことが多い

  • PostgreSQL では ILIKE を使うことで大文字・小文字を無視したマッチングが可能

  • 必要であれば、LOWER() を併用して検索キーとカラムを小文字化して比較する方法もあります。

3. エスケープ処理

検索文字列中にワイルドカード文字(%_)を含めたい場合は、適切にエスケープを行わないと意図しないマッチングをしてしまいます。SQL では ESCAPE 句を使ったり、特殊文字をエスケープ文字で前置したりする必要があります。

 
SELECT * FROM goods WHERE name LIKE '%50\%%' ESCAPE '\';

この例では「50%」という文字列を検索対象に含めたい場合の書き方です。

4. 複数条件との組み合わせ

あいまい検索と他の条件(数値比較、日付範囲、結合など)を組み合わせる際は、WHERE 句の書き方、実行計画、インデックス設計に注意が必要です。
たとえば、部分一致検索を先にするとスキャンが広くなり、結合条件や他の絞り込み条件を後に書いても性能が出にくくなる場合があります。
そのため、可能な限り絞り込み条件(等価比較や範囲条件など)を先に適用する、あるいはサブクエリ・CTE を使って事前に対象を絞るなど工夫するとよいでしょう。

5. 応用例:あいまい検索の代替アプローチ

アプローチ用途・メリット注意点
正規表現検索(REGEXP、~ など)より複雑なパターンマッチングが可能になるパフォーマンスに注意、サポート状況に依存
トークン分割・前処理検索対象をあらかじめトークン化して部分一致を高速化実装が複雑、追加のメンテナンスコストあり
専用全文検索エンジン高速な全文検索、スコア付け、複合検索データ同期や運用コストを考慮
n-gram / trigram 検索部分一致の高速化を狙える技術インデックス設計やメモリ・ストレージ消費に注意

SQL:INDEXのメリットとデメリットについて

業務でデータベースの操作をする場合、データが大量に登録されているテーブルへアクセスする場合に索引(INDEX)を作成するとSQLクエリの実行が劇的に早くなるケースが多々あります。この索引(INDEX)についてどういう場合に作成すれば良いのか、メリット、デメリット等についてまとめておきます。

どういう場合に索引(INDEX)を作成すれば良いのか

索引(INDEX)を作成した方が良いケース

  • 項目数/データ数が多い大規模な表の1%~15%程の行を頻繁にアクセスする場合
  • WHERE句で頻繁に使用されている列である場合
  • 列の値が比較的一意である場合
  • 参照整合性制約で使用されている外部キーになっている列である場合

索引(INDEX)を作成しない方が良いケース

  • データ登録件数が少ない表である場合
  • 列内の値がほぼユニークである場合
  • NULL値が多く、NULL以外の値を検索しない場合

索引(INDEX)のメリット

  • 表検索(SELCET)する際、特定の行を素早く検索する事が出来る為、検索のパフォーマンスが早くなります。
  • ソート作業を省略出来ます。

索引(INDEX)のデメリット

  • データの登録(INSERT)、変更(UPDATE)の際、索引変更のためのオーバーヘッドが加わるため、索引(INDEX)がないテーブルに比べると時間が掛かります。
  • 索引(INDEX)を作成する領域が必要となります。