JavaScript入門 正規表現の使い方

最終更新日

JavaScriptでは、RegExpオブジェクトを使うことで、正規表現を扱うことができます。正規表現とは、文字列をパターンの一致で検索するときに使う記法です。通常の検索では特定の文字列に対する完全一致しか判定できませんが、正規表現を使うことであいまいな検索条件を指定できます。たとえば、ある文字列の羅列から、携帯電話番号のフォーマットに一致する文字列を抽出したい場合、携帯電話の組み合わせの数が膨大となってしまうため、通常の検索では対応できません。一方、正規表現を使うと、次のように特定できます。

基本的な使用方法

不規則な文字列から携帯番号を抽出

const targetString = "5341nb;g090-1234-5678f29q0g070-9876-5432nfwse15des2e";//検索対象の文字列
const mobileNumPattern = /(070|080|090)-\d{4}-\d{4}/g;                      //正規表現の定義
const mobileNums = targetString.matchAll(mobileNumPattern);                 //正規表現を定義
for ( const mobileNum of mobileNums ){
    console.log(mobileNum[0]);
}
実行結果

RegExpオブジェクトの作成

RegExpオブジェクトは、次の2種類の方法でインスタンス化します。

構文:RegExpオブジェクトのインスタンス化

正規表現リテラルを使う場合
let RegExpオブジェクト = /正規表現/[フラグ]

RegExpオブジェクトからインスタンス化する場合
let RegExpオブジェクト = new RegExp("正規表現" [,"フラグ"]);
let RegExpオブジェクト = new RegExp("/正規表現/" [,"フラグ"]);

文字列の場合は文字をシングルクォートなどでくくることで定義しますが、正規表現は/と/でくくることで定義します。また、正規表現を使った検索では、検索モードをフラグによって指定できます。

正規表現リテラルで定義した場合もRegExpオブジェクトが生成される

console.log(/abc/ instanceof RegExp);
>true

そのため、/abc/.test( “テスト文字列” )のように、RegExpのメソッドを続けて呼び出すことができます。

正規表現に関わるメソッド

正規表現に関わるメソッドは、RegExpオブジェクトとStringオブジェクトに格納されています。正規表現で使用可能な特殊文字が使われています。

メソッド戻り値説明
test(testStr)真偽値正規表現がテスト文字列(testStr)内で一致する場合には、trueを返す。それ以外には、falseを返す
/abc/.test( “012abc” );
>true
exec(testStr)配列|nullexecでは、抽出結果を配列として返す。一致箇所がない場合には、nullが返る
/a(b)c(d)e/.exec( “babcde” );

■結果と意味は以下の通り
[
0: “abcde”, //マッチング文字列
1: “b”, //1つ目の()内で一致した文字列
2: “d”, //2つ目の()内で一致した文字列
index: 1,
input: “babcde”,
groups: undefined,
]


[0]:マッチング文字列
[n]:()を使った抽出箇所が要素に追加される
[index]: 一致箇所の開始インデックス
[input]: execの第1引数(testStr
match(regex)配列|null文字列と正規表現(regex)の一致結果を配列で返す。一致箇所がない場合には、nullが返る
“babcde”.match( /a(b)c(d)e/ ); //※1

■結果と意味は以下の通り
[“abcde”, “b”, “d”, index: 1, input: “babcde”]

[0]:マッチング文字列
[n]:()を使った抽出箇所が要素に追加される
[index]: 一致箇所の開始インデックス
[input]: execの第1引数(testStr

※1のように、文字列に続けてメソッドが記述された場合には、ラッパーオブジェクトであるStringオブジェクトのメソッドが呼び出される
matchAll(regex)iteratorObjectr文字列の正規表現(regex)のすべての一致箇所をイテレータ(iteratorObject)として返す。また、matchAll使用時は、globalフラグ(g)を必ず有効にする必要がある

const str = “return request”;
const it = str.matchAll( /re(\S+)/g );
for( const v of it ){
console.log(v);
}
> [“return”, “turn”, index: 0, …]
> [“return”, “quest”, index: 7, …]
replace(regex,replaceStr)replaceStr正規表現(regex)での一致箇所を文字列(replaceStr)で置換した文字列(replacedStr)を返す。また、()で囲んだ箇所は、置換文字列($1~)として使うことができる
“apple, lemon”.replace(/([a-z]+), lemon/, “banana,$1” );
> “banana , apple”
search(regex)index | -1正規表現(regex)が文字列内で最初に一致した箇所のインデックス(index)を返す。一致しなかった場合には、-1が返る
“text”.search(/a/);
>-1
“hello, abc”.search(/a/);
>7
split([separator[, limit]])配列文字列が分割文字(separator)によって分割された配列を返す。分割数の上限は、limitで指定可能。分割文字には、文字列または正規表現を使用可能
“return request response”.split(/\s/); //空白で分割
>[ “return”, “request”, “response” ]

正規表現で使用可能な特殊文字

正規表現で検索パターンを定義するときに使用する特殊文字(メタ文字)の一覧になります。

文字説明
ドット(.)改行文字以外の任意の1文字に一致する(sフラグが有効の場合には、改行文字にも一致する)。具体的には、\n(U+000A)、\r(U+000D)、ラインセパレータ(U+2028)、段落区切り文字(U+2029)以外に一致する
/./.test(“a”); //true
[abc]aまたはbまたはcの1文字に一致する。[]で囲まれた部分は文字クラスト呼ぶ
/[abc]*.test( “apple” ); //true
[^abc]aまたはbまたはc以外の1文字に一致する
/[^abc]/.test( “fs” ); //true
/[^abc]/.test( “ab” ); //false
[a-z]
[A-Z0-9]
[a-z] 半角小文字英字のaからzの1文字に一致する
[A-Z0-9] 半角大文字英字のAからZまたは0から9の1文字に一致する
文字クラス内のハイフン(-)は、範囲を表す
\w半角英数字またはアンダースコア(_)の1文字に一致する。文字クラスで記述した場合には、[a-zA-Z0-9_]になる
/\w\/.test( “_” ); //true
\W\w(半角英数字またはアンダースコア)以外の1文字に一致する。文字クラスで記述した場合は[^a-zA-Z0-9_]になる
/\W\/.test( “_” ); //false
\d0~9の数値1文字に一致する
/\d/.test( “0” ); //true
\D\d(数値)以外1文字に一致する
/\d/.test( “a” ); //true
\sスペース、タブ、改ページ、改行を含むホワイトスペース1文字に一致する。以下の文字クラスに相当する
[\f\n\r\t\v\u00a0\u1680\u180e\u2000-\u200a\u2028\u2029\u202f\u205f\u3000\ufeff]
/\s/.test( ” ” ); //true
\S\s以外の1文字に一致する
/\S/.text( ” ” ); //false
\n改行文字(U+000A)に一致する
\r復帰文字(キャリッジリターン)に一致する
\tタブ(U+0009)に一致する
\v垂直タブ(U+000B)に一致する
^文頭一致を行う(mフラグが有効の場合には、改行文字(\n)の直後の一致も判定対象になる)
/^te/.test( “test” ); //true
/^te/.test( “1test” ); //false
$分末一致を表す(mフラグが有効の場合には、改行文字の直前の一致も判定対象になる)
/st$/.test( “test” ); //true
/st$/.test( “test1” ); //false
{n}
{m,n}
{m,}
{n} 直前の文字がn回繰り返す場合に一致する
{m,n} 直前の文字がm~n回繰り返す場合に一致する
{m,} 直前の文字がm回以上繰り返す場合に一致する
+1回以上の文字の繰り返しを表す
/a+/.test( “bbb” ); //false
/a+/.test( “bab” ); //true
/a+/.test( “aaaa” ); //true
*0回以上の文字の繰り返しを表す
/a*/.test( “” ); //true
/a*/.test( “bab” ); //true
/a*/.test( “bb” ); //true
?直前の文字が0回または1回繰り返す場合に一致する。*、+、?、{}の後ろに使った場合には、マッチング箇所が最短一致になる。最短位置とは、マッチング箇所が最短になることを言う
/.?/.test( “” ); //true
/a+/.test( “aaaA” ); //一致箇所は”aaa”になる
/a+?/.test( “aaaA” ); //一致箇所は”a”になる(最短一致)
(abc)()で囲んだ部分をパターンマッチ箇所として、後方参照で使用できる。後方参照とは、マッチングした箇所を後に再利用することを言う
・同一正規表現内で再利用(\数値)
\数値(1~)で一致部分を再利用できる
/(#)テスト\1/.test( “#テスト#” ); //(#)なので、\1は#と同じ意味
>true


・置換文字列として使用($数値)
$数値(1~)で一致部分を使って置換できる
“<h1>テスト</h1>”.replace(/<h1>(.+)<\/h1>/, “<h2>$1</h2>” );
> “<h2>テスト</h2>”


・一致した文字列を抽出して配列として保持する場合

let result = /a(b)c(d)e/.exec( “abcde” );
console.log(result);
> [“abcde”, “b”, “d”, …];
ab|cdeabまたはcdeの文字列に一致する
/(ab|cde)d/.test( “abd” ); //true
\特殊文字を文字列として表す場合に使用する
/\.\+\(\[\//.test( “.+([/” ); //true

正規表現で使うフラグ

正規表現では、フラグを使うことで状況に応じて、検索モードを変更できます。

フラグの一覧

フラグフラグ名説明
gglobalグローバルサーチ(複数一致)を行う
const str = “return request resource”;
str.match(/re\S+/); //gフラグなし
> [“return”, …] //最初に見つかった一致箇所のみ取得

str.match(/re\S+/g); //gフラグあり
> [“return” , “request” , “resource”] //すべての一致箇所を取得
iignoreCase大文字・小文字を区別しない
/a/i.test( “A” ); //true
mmultiline複数行検索を行う。^を行頭一致(行の開始に一致)、$を行末一致(行の終わりに一致)として扱う
const multipleLines = `aaa
bbb
ccc`;
multipleLines.match(/^.+$/mg); //行ごとの文字列にマッチ
>[ “aaa”, “bbb” , “ccc” ]
sdotAllドット(.)の一致対象に改行文字を含める
/./.test( “\n” ); //false
/./s.test( “\n” ); //true
uunicodeサロゲートペア※1に対応する完全なUnicode文字列としてパターンマッチを行う。絵文字などがそれにあたる

/^.$/.test( “🥺” ); //false サロゲートペアの考慮がないため1文字として扱われない
/^.$/u.test( “🥺” ); //true uフラグにより1文字として扱われる


※1JavaScriptの場合は、UTF-16(16bitで1つの文字を表す)で文字を表現しますが、Unicodeで使用可能な文字が増えたことにより、2つ分の文字コードで1文字を表す必要がでてきました。このような2つ分の文字コードで1文字を表す方式をサロゲートペアと言います。
ystickylastIndexプロパティに示されたインデックスからの前方一致(語頭部分の一致)を判定する
const str = “return request resource”;
const reg = /re\S+/y;
reg.lastIndex = 0; //初期値は0
reg.exec(str);
> [“return”, …] //0番目の文字列から検索

reg.lastIndex = 7;
reg.exec(str);
> [“return”, …] //7番目の文字列から検索