正規表現で、エスケープが必要となる特殊文字をまとめました。
目次
正規表現でエスケープが必要な文字
正規表現では、特殊文字を文字として認識させたい時、バックスラッシュ(\)を使ってエスケープ(迂回)を行います。
「あれ、この文字はエスケープが必要だったけ?」記憶が曖昧になることが多々ありますので、下記にまとめていきます。
1メタ文字はもれなくエスケープが必要
正規表現で「メタ文字」などと呼ばれる特殊文字は、もれなくエスケープが必要です。下記はメタ文字の一覧です。必要な場合はエスケープしましょう。
正規表現 | エスケープ後 | メタ文字の意味 |
---|---|---|
. | \. | 改行(\n、\r)を除くすべての文字 |
^ | \^ | 行頭の位置(シングルラインモード:行頭、マルチライン:文章の頭) |
$ | \$|行末の位置 | |
| | \| | 「|」の左右の文字列のいずれか |
\ | \\ | 直後のメタ文字をエスケープする |
[、または、] | \[, \] | 文字クラスの開始、終了を表す。 |
(、または、) | \(, \) | サブパターンの開始、終了を表す。 |
{、または、} | \{, \} | 量指定子の開始、終了を表す。 |
+ | \+ | 1回以上の繰り返し |
* | \* | 0回以上の繰り返し |
? | \? | 0回、もしくは1回の出現 |
2デリミタと同じ文字はエスケープが必要
正規表現パターン記述の中で、デリミタとの混同を避けるため、デリミタに利用した文字と同じ文字が出現するのであれば、それらはエスケープする必要があります。
Vimや、PHP(PCRE正規表現)などの多くのプログラミング言語においては、正規表現パターンは、そのパターンの開始と終了を同一の任意の文字で囲むことになっています。これらの囲み文字を「デリミタ(delimiter)」と呼ばれます。
デリミタにはどんな文字を使っても構いませんが、一般的にスラッシュ「/」がよく用いられます。(Javascriptでは、リテラルによる宣言(例:var ptn = /pattern/)によるデリミタは「/」のみ認めらています。)
//「/」がデリミタなので、パターン中ではエスケープする
$ptn = '/https:\/\/www-creators.com\/archives\/3102/';
但し、上記の例のように元々スラッシュが多く現れる「URL文字列」や「ディレクトリパス」が、パターンに含まれる場合、正規表現を記述しにくくなってしまいます。
そのような場合、「#」「~」「@」など別の文字を代わりにデリミタとする事で、エスケープが不要になります。このような工夫によって、正規表現パターンをより読みやすく記述することができるでしょう。
// デリミタを「#」とすることで、スラッシュはエスケープが不要。
$ptn = '#https://www-creators.com/archives/3102#';
文字列表現中のバックスラッシュ
PHPにおいて、クオーテーションを利用した文字列表現においては、「\(バックスラッシュ)」が、「直後の文字を通常文字として扱う」と行った文字エスケープの意味を持っています。このPHP文字列表現におけるエスケープ機能は、正規表現としてのエスケープ機能を無効化していしまいますので、注意が必要です。これを迂回するため、エスケープにエスケープを重ねる必要があります。見た目が非常の紛らわしいので注意して下さい。
//「\」をマッチする正規表現パターン
$ptn = '#\\\\#';
わかりにくいですよね。正規表現自体は「\\」ですが、php による\の無効化を回避するためそれぞれの「\」に「\」が追加されています。
PHPドキュメントもあわせてどうぞ:
3文字クラス内の特殊文字はエスケープが必要
上記のメタ文字一覧にもありますが、「[」、「]」で文字を囲むと、文字クラスと呼ばれた特別な表現になります。
このような文字クラスにおいては、前述のような正規表現の通常のメタ文字は特別な意味をもちませんのでエスケープが不要になります。
// !、?、+, a、のいずれかの一文字。エスケープは不要
[?!+a]
一方で、文字クラス内でのみ特殊な意味をもつ「-」や「]」はエスケープが必要です。「[」はエスケープは不要ですが、エスケープしても構いません。
下記は紛らわしい例の1つです(このようなパターンが必要になる事が、本当にあるかどうかは疑問ですが・・・)
// 「-」、「[」、「]」のいずれかの文字
[\[\-\]]
また「文字クラスの否定」を表す「^」は文字クラス開始の「[」の直後でのみ意味を持ちますので、文字クラスの開始が、文字としての「^」であれば、エスケープが必要です。ただし、単純に「^」を開始に配置するのを避けたほうがシンプルでしょう。
// $, #, %, ^ のいずれか
[\^$#%]
// はじめからこのように 冒頭に ^ を避ければ良い。下記は同義:
[#$%^]
ちなみに、「否定の文字クラス」については、こちらの記事に言及しています。ご参考まで。
正規表現のエスケープに関する参考情報
メタ文字やエスケープシーケンスについては、こちらの記事もご覧ください
上記で、「文字クラスの否定」に言及しましたが、興味があれば、こちらの人気記事もご覧ください。
PHP公式ドキュメントでは、PHPでの正規表現にデフォルトに採用されているPCREについて、網羅的な解説があります。PCREとは、Perl 5と同じ文法構文を使った正規表現処理の関数ライブラリです。PCREについて、詳しい情報はこちらが参考になるでしょう。
バックスラッシュ自信も、エスケープ対象なんだね。