SQLで全角文字と半角文字を判定するにはLENGTHBやOCTET_LENGTH関数で取得したバイト数とLENGTH関数で取得した文字数を比較することで判断することができます。
使用例
- サンプルテーブル「goods」
- クエリー(SQL)
ORACLEの場合はOCTET_LENGTHをLENGTHBへ変更すれば同様の結果を得られます。
1234SELECT SELECT nameFROM goodsWHERE name is NOT NULLAND LENGTH(name) <> OCTET_LENGTH(name); - 出力結果
補足
1. 判定ロジックの背景と利用ケース
-
全角文字・半角文字を判定する目的として、データ品質管理(例:ユーザー登録時の文字種チェック)、システム移行時の文字コード整合性確認、レポートや印刷用データの整形などが考えられます。
-
特にマルチバイト文字(日本語)環境では、1文字あたりのバイト長が異なるため、バイト長と文字数のずれを利用した判定が有効です。
-
本記事で紹介されているように、例えば PostgreSQL の
LENGTH()とOCTET_LENGTH()の比較を使う方法はシンプルでクロスプラットフォームにも応用可能です。
2. 各データベースでの関数違い・注意点
-
PostgreSQL:文字数を返す
LENGTH(text)、バイト長を返すOCTET_LENGTH(text)を使う。
例:WHERE length(col) <> octet_length(col) -
Oracle:Oracle には直接
OCTET_LENGTHがないが、LENGTHB()がバイト長を、LENGTH()が文字数を返す(ただしCHAR型/NCHAR型、CHARSET設定によって挙動が異なる)ので、LENGTHB(col) <> LENGTH(col)という書き方が使えます。 -
MySQL:
CHAR_LENGTH(col)が文字数、LENGTH(col)がバイト数を返すので、CHAR_LENGTH(col) <> LENGTH(col)といった判定が可能。 -
SQL Server:
LEN()が文字数(末尾の空白はカウントされない)、DATALENGTH()がバイト長(文字コード依存)を返すので、環境次第ではLEN(col) * 2 <> DATALENGTH(col)などと併用するケースがあります。 -
注意点として、文字コード(UTF-8、UTF‐16、Shift_JIS 等)が環境によって異なると「半角=1バイト」「全角=2バイト」という前提が崩れる場合があります。特にUTF-8では日本語全角文字が3バイトある場合もありますので、バイト数の比較ロジックを適用する際は対象の文字コードを意識してください。
3. 実運用的な工夫・パフォーマンス面の注意
-
大規模テーブルでこのようなチェックを行う場合、たとえば
WHERE LENGTH(col) <> OCTET_LENGTH(col)のような関数を大量の行に対して実行するとインデックスが効かず、全表スキャンになる可能性があります。-
解決策:バッチ処理的に時間帯を分けて実施、あるいはチェック専用にサマリテーブルを用意する。
-
また、事前に「文字種/文字コード/想定バイト数」などのデータ仕様を設け、そもそも混在しないように制御するのが望ましいです。
-
-
判定だけでなく、誰がいつどのレコードを修正したか(=トレーサビリティ)を残すなら、更新日時・更新者カラムを活用して「チェック済み/要修正」などのフラグを設けると管理しやすくなります。
-
将来的に正規表現(REGEXP)や文字列関数(例えば Unicode プロパティを利用した判定)を使って「半角カタカナ」「全角英数字」「漢字のみ」などより細かく制御したい場合も多いため、可能ならその準備もしておくと良いでしょう。
4. よくある誤り・ハマりどころ
-
前提として「文字数とバイト数が異なる=全角含む」という仮定をしているため、 半角カタカナ や 絵文字(マルチバイト4バイトなど) が含まれていると誤検知される可能性があります。たとえば、UTF-8環境で絵文字が4バイトなので「文字数1、バイト数4」→「異なる」と判定されてしまう。
-
文字コード設定の違い:テーブル/カラムごとに異なる照合順序・文字セットが指定されていると、バイト数や文字数の挙動が予想と異なることがあります。例えば MySQL で
utf8mb4を使っているなら日本語全角文字が3バイトではなく4バイトになるケースあり。 -
更新系の処理で「半角に変換された/全角に変換された」履歴を残していないため、修正したデータが「元はどちらだったか」が分からなくなるという運用上のリスク。必要に応じて「修正前の値」保持やログ出力を検討するべきです。
5. 具体的な応用例・コードスニペット
PostgreSQL での運用例
MySQL での運用例
Oracle での運用例
6. フォローアップ可能な内容・発展トピック
-
正規表現を用いて「全角ひらがな」「全角カタカナ」「全角英数字」「半角英数字」などを分類・抽出する方法。
-
文字種に応じて別テーブルへアーカイブ・除外といったワークフロー設計。
-
BI/レポート用途で「文字種別カウント」を可視化する方法(例:Excel/Tableau/BIツールを用いた文字種分布グラフ化)。
-
外部システム(CSV/Excel)からデータインポート時に「文字種チェック+自動整形(全角→半角、半角→全角)」を組み込むETL(Extract-Transform-Load)設計。
-
将来的に多言語対応を視野に入れた「Unicodeカテゴリ判定」(たとえば、CJK文字・ラテン文字・Emoji など)を含めた文字種チェック。
