Vimで使える正規表現

/web/tool

Note: この記事は、3年以上前に書かれています。Webの進化は速い!情報の正確性は自己責任で判断してください。

Vimの正規表現をまとめてみました。Vimの正規表現は——基本的にコマンドモードで使うためか——やたらエスケープが多かったりして、ちょいと独特です。また、拡張正規表現も使えないので、Perlのノリで書くとやきもきしますね。以下、検索に関わりそうなオプション設定。

:set wrapscan 折り返し検索を有効にする
:set ignorecase 大文字と小文字の区別をしない
:set smartcase 検索文字列に1字でも大文字が含まれていたら、大文字と小文字を区別する
(ignorecaseがオンの時)
:set magic 正規表現に使われる記号を有効にする
(:set nomagicだと、「*」は文字“*”にマッチする。「\*」で繰り返し。)

memo: いちお、eregexというプラグイン入れればPerl5の拡張表現は使えます

用例(検索)

/foo\|beep fooかbeep
/foo[0-9] foo2とかfoo9とか
/foo/b2 fooにマッチし、カーソルを2文字分移動

OR演算子にエスケープが必要だったり、検索時にカーソル位置のオフセットを指定できる辺り、なかなか珍しいですね。Sig.はあまり使わないけれど、「/foo/e5」とか「/foo/-3」とか試してみると面白いですよ。

単純なatom

. 任意の一文字にマッチ
^ 行の最初にマッチ(パターンの最初に置かれて)
$ 行の最後にマッチ(パターンの最後に置かれて。"\|" の前とか"\)"の前でも同じ)
\< 単語の最初にマッチします
\> 単語の最後にマッチします

修飾子

基本の繰り返し \* 0回以上の繰り返しにマッチします (最大マッチ)
\+ 1回以上の繰り返しにマッチします (最大マッチ)
\= 0回もしくは1回にマッチ
最大マッチ \{n,m} n回からm回までの繰り返しにマッチ
\{n} n回の繰り返しにマッチ
\{n,} n回以上の繰り返しにマッチ
\{,m} 0回からm回までの繰り返しにマッチ
\{} 0回以上の繰り返しにマッチ(* と同じ)
最小マッチ \{-n,m} n回からm回までの繰り返しにマッチ
\{-n} n回の繰り返しにマッチ
\{-n,} n回以上の繰り返しにマッチ
\{-,m} 0回からm回までの繰り返しにマッチ
\{-} 0回以上の繰り返しにマッチ

特別なatom

文字・数字 \a [a-zA-Z] アルファベット文字
\A [^a-zA-Z] アルファベット以外の文字
\d [0-9]
\D [^0-9] 数字以外の文字
\w [0-9A-Za-z_] 英数字
\W [^0-9A-Za-z_] 英数字以外の文字
\s [[:blank:]] ホワイトスペース文字
\S [^[:blank:]] ホワイトスペース以外の文字
文字の種類 \l [a-z] 小文字
\L [^a-z] 小文字以外の文字
\u [A-Z] 大文字
\U [^A-Z] 大文字以外の文字
\h [A-Za-z_] 単語の頭文字
\H [^A-Za-z_] 単語の頭文字以外の文字
記数法 \x [0-9A-Fa-f] 16進数
\X [^0-9A-Fa-f] 16進数でない文字
\o [0-7] 8進数
\O [^0-7] 8進数でない文字
特殊な文字 \e [[:escape:]] <Esc>
\t [[:tab:]] <Tab>
\r [[:return:]] <CR>
\b [[:backspace:]] <BS>

atomを使うほうが範囲指定よりも速い ...が、大抵は知覚できるほどじゃない

後方参照

\~ 最後に行われた置換文字列にマッチします
\(abc\) エスケープされた括弧で囲まれたパターン。後の使用のためにグループ化する。
\1 "\(" と "\)" 内のパターンに一致した1番目の文字列にマッチ。
\2 同上。2番目の文字列にマッチ
\9 同上。9番目の文字列にマッチ

いわゆる「捕捉のための括弧」ですね。主に置換で使います。「:%s/\(abc\)/\1def/g」みたいな感じで。

範囲

用例 [abc] a,b,cいずれか任意の文字にマッチします
[^abc] a,b,c以外の文字にマッチします
[a-z] aからzまでの全ての文字に一致(文字コードの範囲指定)
[a-z0-9] aからzまでと0から9までの全ての文字に一致
文字クラス表現 [:alpha:] アルファベット
[:alnum:] アルファベットとアラビア数字
[:blank:] スペースとタブ文字
[:space:] ホワイトスペース文字
[:digit:] 10進数
[:xdigit:] 16進数
[:graph:] スペースを除いた印字可能な文字
[:print:] スペースを含めた印字可能な文字
[:upper:] アルファベットの大文字
[:lower:] アルファベットの小文字
[:punct:] 句読点文字
特殊な文字 [:cntrl:] 制御文字
[:return:] <CR> 文字
[:tab:] <Tab> 文字
[:escape:] <Esc> 文字
[:backspace:] <BS> 文字

範囲指定の中で使う文字クラス表現は、以下のように使います。

  1. /[-./[:alnum:]_~]\+

つまり、範囲指定の[]と文字クラスの[]は別のもの。Perlと違って[]の中では\sとか使えないので、覚えておくと良い。

こういうのはPOSIXクラスというらしい。たとえばエストニア語のアルファベットでは[sztuvwxy]と続くため[a-z]ではすべてのアルファベット小文字にマッチしない。つまり、文字列の範囲はロケールに依存する。なので上記のようにして文字の区分を表すのだとか。

Note: スパム対策が面倒なので、コメント投稿を廃止しました。以前のコメントは残します。
ご意見・ご要望はtwitter@sigwygかはてブコメントにて。

2 Comments

Anonymous wrote:
magick → magic
じゃないですか? 2009–07–04 15:50
Sig. wrote:
お、ホントだ!
ありがとうございます。

ついでに少し見やすくしてみました。 2009–07–05 02:38