title=正規表現


正規表現(regular expression)は文字列のパターンを記述するための言語です。
また、この言語で記述されたパターンも正規表現と呼びます。

正規表現を用いると、文字列が指定したパターンを含んでいるかどうかを判定し、
また含んでいるならばそれが文字列中のどの場所であるかを知ることができます。
  /pat/
  %r{pat}
などの正規表現リテラルや [[m:Regexp.new]] などで正規表現
オブジェクトを得ることができます。


=== メタ文字列とリテラル、メタ文字とエスケープ
正規表現の文法には、正規表現内で特別な働きをする文字列と、それ以外の
その文字列そのものにマッチするような文字列があります。
前者をメタ文字列(meta string)、後者をリテラル(文字列)(literal string)と呼びます。
  /京都|大阪|神戸/
という正規表現においては、「京都」「大阪」「神戸」がリテラルで、
2つの「|」がメタ文字列です。

以下の文字は「メタ文字」(meta character)
と呼ばれる、正規表現内で特殊な働きをする文字です。
  ( ) [ ] { } . ? + * | \
これらの文字をリテラルのようにその文字としてマッチさせるためには、
バックスラッシュ「\」を前に付けます。「\\」はバックスラッシュ1文字に
マッチします。

メタ文字以外の文字も、メタ文字に続けて置くことで特別な働きをするよう
になる場合があります。つまりメタ文字列を構成します。例えば
  /[a-z]/
  /\Axyz\Z/
という正規表現において "[a-z]", "\A", "\Z"はメタ文字列です。

=== 式展開
正規表現内では、#{式} という形式で式を評価した文字列を埋め込むことが
できます。
  place = "東京都"
  /#{place}/.match("Go to 東京都") # => #<MatchData "東京都">

埋め込んだ文字列にメタ文字が含まれているならば、それは
メタ文字として認識されます。
  number = "(\\d+)"
  operator = "(\\+|-|\\*|/)"
  /#{number}#{operator}#{number}/.match("43+291") 
  # => #<MatchData "43+291" 1:"43" 2:"+" 3:"291">

埋め込む文字列をリテラルとして認識させたい場合は [[m:Regexp.quote]] を
使います。

=== 文字
正規表現内では、「\」の後に文字列を置くことで、
ある特定の文字を表現することができます。
これは、改行のように Ruby の文法で特別な意味を持つ文字を埋め込む
ためなどに用いられます。
文字列リテラルの記法とほぼ同様([[ref:d:spec/literal#backslash]])で、
以下の記法が利用可能です。

  \t           水平タブ            horizontal tab (0x09)
  \v           垂直タブ            vertical tab   (0x0B)
  \n           改行                newline        (0x0A)
  \r           復帰                return         (0x0D)
  \b           バックスペース      back space     (0x08)
  \f           改ページ            form feed      (0x0C)
  \a           ベル                bell           (0x07)
  \e           エスケープ文字      escape         (0x1B)
  \nnn         符号化バイト値の8進数表現 (nnn の8進数3文字で表現)
  \xHH         符号化バイト値の16進数表現 (HH の16進数2文字で表現)
  \cx, \C-x    制御文字 (x は a から z までのいずれかの文字)
  \M-x         メタ (x|0x80)
  \M-\C-x      メタ制御文字 
  \uHHHH       ユニコード文字 (HHHH の16進数4桁)
  \u{HHHHHH HHHHHH ....} ユニコード文字列 (HHHHHH は16進数1桁から6桁まで指定可能)
\b は文字クラス内でのみ有効な表現です。文字クラスの外では
単語の区切りを表すメタ文字列と解釈されます。

「\s」は文字列では空白(0x20)を意味しますが、正規表現では
タブなどを含む空白文字全般にマッチするメタ文字列です。


=== 任意の1文字
メタ文字 . は改行を除く任意の1文字にマッチします。

ただし、オプション m によって改行にもマッチするようになります。

===[a:string] 文字クラス

文字クラス(character class)
とは角括弧 [ と ] で囲まれ、1個以上の文字を列挙したもので、
いずれかの1文字にマッチします。
  /W[aeiou]rd/
は Ward, Werd, Wird, Word, Wurd のいずれかにマッチします。

文字クラス内のハイフン(-)は文字の範囲を表すメタ文字です。
例えば [abcd] という文字クラスは [a-d] と表すことができます。
複数の範囲指定をすることもできます。例えば [abcdpqrs] は [a-dp-s]と
表すこともできます。

文字クラスの [ の直後の文字がキャレット(^)である場合、列挙「されていない」
文字にマッチするようになります(これは否定文字クラスと呼ばれます)。
  [^a-d]
はabcd以外の1文字にマッチします。

文字クラス内に別の文字クラスを含めることができます。
[a-z[0-9]] は [a-z0-9]と同じ意味を持ちます。これだけではあまり意味が
ありませんが、文字クラスは && という、共通部分を取る演算をサポートして
いるため、これと組合せることで意味を持ちます。
  /[a-z[0-9]]/.match("y") # => #<MatchData "y">
  /[a-z[0-9]]/.match("[") # => nil
  r = /[a-w&&[^c-g]e]/ # ([a-w] かつ ([^c-g] もしくは e)) つまり [abeh-w] と同じ
  r.match("b") # => #<MatchData "b">
  r.match("c") # => nil
  r.match("e") # => #<MatchData "e">
  r.match("g") # => nil
  r.match("h") # => #<MatchData "h">
  r.match("w") # => #<MatchData "w">
  r.match("z") # => nil

文字クラスでは、否定(^)範囲(-)共通部分(&&)列挙(並べる)という
演算が可能ですが、これらは - > (列挙) > && > ^ という順の結合強度を持ちます。

文字クラス内の3つのメタ文字を通常の文字の意味で使用したい場合には、
\ によってエスケープ する必要があります。

==== 文字クラスの略記法
良く使われる文字クラスには省略記法が存在します。
  * \w 単語構成文字 [a-zA-Z0-9_]
  * \W 非単語構成文字 [^a-zA-Z0-9_]
  * \s 空白文字 [ \t\r\n\f\v]
  * \S 非空白文字 [^ \t\r\n\f\v]
  * \d 10進数字 [0-9]
  * \D 非10進数字 [^0-9]
  * \h 16進数字 [0-9a-fA-F]
  * \H 非16進数字 [^0-9a-fA-F]
これらの「空白」「数字」などは ASCII の範囲の文字のみを対象としています。
いわゆる「全角アルファベット」「全角空白」「全角数字」などは
ここの空白、数字、には含まれません。
  /\w+/.match("ＡＢＣｄｅｆ") # => nil
  /\W+/.match("ＡＢＣｄｅｆ") # => #<MatchData "ＡＢＣｄｅｆ">
  /\s+/.match("　") # => nil
  /\S+/.match("　") # => #<MatchData "　">
これらは文字クラス内で演算することもできます。
  r = /[\d&&[^47]]/ # 4, 7 以外の数字
  r.match("3") # => #<MatchData "3">
  r.match("7") # => nil

==== Unicode プロパティによる文字クラス指定
また、Unicodeのプロパティ(属性情報)による文字クラス指定も可能です。
以下の記法が使えます。
  * \p{property-name}
  * \p{^property-name} (否定)
  * \P{property-name} (否定)
サポートされているプロパティのリストは
[[url:https://github.com/k-takata/Onigmo/blob/master/doc/UnicodeProps.txt]] を
参考にしてください。また、プロパティの意味は Unicode の仕様を参照してください。
  /\p{Letter}+/.match(".|あaＡＢｃ123") # => #<MatchData "あaＡＢｃ">

==== POSIX 文字クラス
Unicodeプロパティと
似た機能を持つ記法として、POSIX 文字クラスと呼ばれるものがあります。
これらは上の省略記法とは異なり、文字クラスの中でしか用いることが
できません。これらは [:クラス名:] という記法を持ちます。
また、[:^クラス名:]という記法でその否定を意味します。
以下の括弧では実際にどの文字にマッチするかが Unicode プロパティや
Unicode コードポイントで示されています。
  * [:alnum:] 英数字 (Letter | Mark | Decimal_Number)
  * [:alpha:] 英字 (Letter | Mark)
  * [:ascii:] ASCIIに含まれる文字 (0000 - 007F)
  * [:blank:] スペースとタブ (Space_Separator | 0009)
  * [:cntrl:] 制御文字 (Control | Format | Unassigned | Private_Use | Surrogate)
  * [:digit:] 数字 (Decimal_Number)
  * [:graph:] 空白以外の表示可能な文字(つまり空白文字、制御文字、以外) ([[:^space:]] && ^Control && ^Unassigned && ^Surrogate)
  * [:lower:] 小文字 (Lowercase_Letter)
  * [:print:] 表示可能な文字(空白を含む) ([[:graph:]] | Space_Separator)
  * [:punct:] 句読点 (Connector_Punctuation | Dash_Punctuation | Close_Punctuation | Final_Punctuation | Initial_Punctuation | Other_Punctuation | Open_Punctuation)
  * [:space:] 空白、改行、復帰 (Space_Separator | Line_Separator | Paragraph_Separator | 0009 | 000A | 000B | 000C | 000D | 0085)
  * [:upper:] 大文字 (Uppercase_Letter)
  * [:xdigit:] 16進表記で使える文字 (0030 - 0039 | 0041 - 0046 | 0061 - 0066)
  * [:word:] 単語構成文字 (Letter | Mark | Decimal_Number | Connector_Punctuation)
これらの POSIX 文字クラスは \s といった省略記法と異なり、
ASCIIコード範囲外の空白などを考慮に入れます。
  /[[:alnum:]]+/.match("abＡＢ１２1") # => #<MatchData "abＡＢ１２1">
  # \u3000 は全角空白
  /[[:graph:]]/.match("\u3000") # => nil
  /[[:blank:]]/.match("\u3000") # => #<MatchData "　">
  /[[:alnum:]&&[:^lower:]]/.match("ａＡ") # => #<MatchData "Ａ">
  /[[:print:]&&[:^lower:]]/.match(" ") # => #<MatchData " ">


注: POSIX ではここで言う文字クラスのことを「ブラケット表現」と
呼び、[:xxx:] というのを文字クラス、と呼んでいいます。よって、
POSIX文字クラス、というのは厳密には
「POSIXブラケット表現における文字クラス」と呼ぶべきものですが、
ここでは「POSIX文字クラス」と呼ぶことにします。

注: [:word:] と [:ascii:] は POSIX では定義されていません。
Ruby/Oniguruma/Onigmo独自のものです。

注: エンコーディングによってこれらの POSIX 文字クラスの挙動が
異なります。上に書いている「マッチする文字」は Unicode 系統の
エンコーディングで使われるものです。
Unicode 系統以外のものは Onigmo の
ドキュメントを参照してください。





=== 繰り返し

以下のメタ文字列は繰り返しを表現します。
直前の部分式を何回繰り返すかを指定します。このような繰り返しを
表すメタ文字列を量指定子(quantifier)と呼びます。
  * * 0回以上
  * + 1回以上
  * ? 0回もしくは1回
  * {n} ちょうどn回(nは数字)
  * {n,} n回以上(nは数字)
  * {,m} m回以下(mは数字)
  * {n,m} n回以上m回以下(n,mは数字)

以下の例で、量指定子の基本的な使いかたを示しています。
  # 以下の正規表現は 最初に大文字が1文字以上(H)で、小文字が1文字以上(l)、
  # lが2文字(ll)の後ろにoが続く文字列にマッチします。
  "Hello".match(/[[:upper:]]+[[:lower:]]+l{2}o/) # => #<MatchData "Hello">
  
これらは「欲張り(greedy)」にマッチします。
マッチが成功する、最長の文字列にマッチしようとします。
そのため、これらの量指定子は特に最大量指定子(greedy quantifier)
と呼ばれます。

==== 最小量指定子(reluctant quantifier)
一方、以下のメタ文字列(普通の繰り返しメタ文字列に ? を付加したもの)
はマッチが成功する、最短の文字列にマッチします。そのため、これらの
量指定子は特に最小量指定子(reluctant quantifier)と呼ばれます。
  * *? 0回以上
  * +? 1回以上
  * ?? 0回もしくは1回
  * {n,}? n回以上(nは数字)
  * {,m}? m回以下(mは数字)
  * {n,m}? n回以上m回以下(n,mは数字)
以下の例では、最小量指定子を使うことで、(\d+)がマッチする場所を変えています。
  /^.*(\d+)\./.match("Copyright 2013.")  # => #<MatchData "Copyright 2013." 1:"3">
  /^.*?(\d+)\./.match("Copyright 2013.")  # => #<MatchData "Copyright 2013." 1:"2013">
また、ネストしていない括弧の対応を取るためにも使えます。
  # ここでは <b> と </b> の対応を取る
  %r{<b>.*</b>}.match("<b>x</b>y<b>z</b>") # => #<MatchData "<b>x</b>y<b>z</b>">
  %r{<b>.*?</b>}.match("<b>x</b>y<b>z</b>") # => #<MatchData "<b>x</b>">

==== 絶対最大量指定子(possessive qualifier)
以下のメタ文字列は、最大量指定子のように最長のマッチをしますが、
一度マッチすると、その後マッチに失敗してもバックトラックしません。
つまりマッチ済みの文字列を手放さずにマッチに失敗します。
これらの量指定子は絶対最大量指定子と呼ばれます。
  * *+ 0回以上
  * ++ 1回以上
  * ?+ 0回もしくは1回
アトミックグループを用いることで同じことができます。

=== キャプチャ
丸括弧 ( ) によってキャプチャをすることができます。
括弧に囲まれた部分正規表現にマッチした
前からn番目の開き括弧によって囲まれた部分式にマッチした
文字列を後で参照することができます。

正規表現内では \1, \2, ... という記法で後方参照できます。
また、\k<1>, \k<2>, ... や \k'1', \k'2', ... という記法を使うこと
もできます(10を越える数字を渡すことができます)。
また、[[m:Regexp#match]] で得られた
MatchData からは [[m:MatchData#[] ]]で取り出せます。

また、[[m:$1]], $2, ... という特殊変数によって n 番目の括弧にマッチした
部分文字列を参照できます。これらの特殊変数はマッチ処理が終わったあとで
しか使えないことに注意してください。
  # (..) に at がマッチしたのを \1 で参照し、マッチが成功している。
  m = /[csh](..) [csh]\1 in/.match("The cat sat in the hat") 
  # => #<MatchData "cat sat in" 1:"at">
  # Regexp#match でマッチしたテキストは MatchData#[] で参照できる
  m[1] # => "at"

1,2,... ではなく、名前を付けることができます。
(?<name>pat)もしくは(?'name'pat)と記述します。キャプチャした文字列は
[[m:MatchData#[] ]] に [[c:Symbol]] を渡すことで参照できます。
これは名前付きキャプチャと呼ばれます。
  m = /\$(?<dollars>\d+)\.(?<cents>\d+)/.match("$3.67")
  # => #<MatchData "$3.67" dollars:"3" cents:"67">
  m[:dollars] # => "3"
  m[:cents] # => "67"

名前付きキャプチャは正規表現内で \k<name>、\k'name' という記法で参照できます。
  /(?<vowel>[aeiou]).\k<vowel>.\k<vowel>/.match('ototomy')
  # => #<MatchData "ototo" vowel:"o">

注: 名前付きキャプチャと数字によるキャプチャは併用できません。


リテラル正規表現内に名前付きキャプチャがあり、 =~ の左辺で用いた
場合には、その名前のローカル変数にキャプチャした文字列を
代入します。
  /\$(?<dollars>\d+)\.(?<cents>\d+)/ =~ "$3.67" # => 0
  dollars # => "3"
  cents # => "67"

数字による後方参照では、負の数による、
\k<-1>, \k<-2>, ... や
\k'-1', \k'-2', ... という記法での
相対的な指定が可能です。-1 は後方参照が書かれた位置の1つ手前の
位置にあるキャプチャを表し、-2, -3, で2つ手前、3つ手前を表します。
これは非常に多くのキャプチャを持つような正規表現を記述するためや、
正規表現に別の正規表現を式展開で埋め込む場合などに便利です。
  /(.)(.)\k<-2>\k<-1>/.match("xyzyz") # => #<MatchData "yzyz" 1:"y" 2:"z">


=== グループ
丸括弧は部分式をグループ化するためにも使えます。( ) で囲まれた
部分式は一つのものとして取り扱われ、量指定子などを続けて書くことができます。

    # The pattern below matches a vowel followed by 2 word characters:
    # 'aen'
    /[aeiou]\w{2}/.match("Caenorhabditis elegans") #=> #<MatchData "aen">
    # Whereas the following pattern matches a vowel followed by a word
    # character, twice, i.e. <tt>[aeiou]\w[aeiou]\w</tt>: 'enor'.
    /([aeiou]\w){2}/.match("Caenorhabditis elegans")
        #=> #<MatchData "enor" 1:"or">

(?:pat) という記法を使うとキャプチャせずにグループ化することができます。
性能が多少改善する場合がありますが、多少見にくくなります。
  # 最初のキャプチャは n で二番目のキャプチャが ti であり、
  # \2 で二番目のキャプチャを後方参照しています
  /I(n)ves(ti)ga\2ons/.match("Investigations")
      # => #<MatchData "Investigations" 1:"n" 2:"ti">
  # 最初のグループは (?: ) を使っているのでキャプチャが作られず、
  # 1番目は ti がキャプチャされます。
  # そして ti を \1 で参照しています。
  /I(?:n)ves(ti)ga\1ons/.match("Investigations")
      # => #<MatchData "Investigations" 1:"ti">

==== アトミックグループ(atomic grouping)
(?>pat) という記法で「アトミック」なグループを作れます。

通常の正規表現では、ある部分式がマッチに成功した後、
続く式がマッチに失敗した場合、
バックトラックによって成功した部分の一部を手放して
マッチにリトライします。
しかし、アトミックなグループがマッチした後、
後続の式がマッチに失敗した場合、一部だけを
バックトラックで巻き戻すのではなく、
このグループのマッチ全体を巻き戻します。
つまり、正規表現のマッチのバックトラックを抑制します。

典型的にアトミックグループはバックトラックの回数を減らし
正規表現を高速化するために用います。

  # 以下のマッチはまず .* が Quote" にマッチした後、
  # 正規表現末尾の " のマッチに失敗します。その後
  # 一文字だけバックトラックして、" のマッチに成功します。
  /".*"/.match('"Quote"') # => #<MatchData "\"Quote\"">
  # 一方、以下のマッチはまず .* が Quote" 全体にマッチした後、
  # 正規表現末尾の " のマッチに失敗します。その後
  # バックトラックで"がマッチした状態まで戻り、
  # (?>.*)以外の選択子がないのでマッチ全体が失敗します。
  /"(?>.*)"/.match('"Quote"') # => nil
  # 一方、以下のマッチはまず .* が Quote" 全体にマッチした後、
  # 正規表現末尾の " のマッチに失敗します。その後
  # バックトラックで"がマッチした状態まで戻り、
  # 次の可能性(つまり | の右側)のマッチを試します。
  # 結果としてマッチが成功します。
  /"(?:(?>.*)|(.*))"/.match('"Quote"') # => #<MatchData "\"Quote\"" 1:"Quote">

=== 部分式呼び出し(subexpression call)
\g<name> もしくは \g'name'
という記法で、nameと名付けられた部分正規表現にマッチしようとします。
この記法は、部分式呼び出しと呼ばれます。
name には名前、数字、のいずれを用いることもできます。
これは後方参照とは異なります。後方参照は前でマッチした文字列と
同じ文字列にマッチしようとしますが、部分式呼び出しは
nameと名付けられた「部分正規表現」にマッチしようとします。

部分式呼び出しの記法は正規表現内に再帰的記述を可能とし、
通常の正規表現では記述不可能な処理(例えば対応した括弧の検出)
を可能とします。以下の例では実際に何回かっこがネストしていても
マッチに成功します。ただし、再帰的な正規表現を書く場合は、
無限ループに陥る可能性があるため、停止条件に注意して
この機能を使ってください。
  /\A(?<paren>\(\g<paren>*\))*\z/ =~ '(())' # => 0 
  # ^1
  #      ^2
  #           ^3
  #                 ^4
  #      ^5
  #           ^6
  #                      ^7
  #                       ^8
  #                       ^9
  #                           ^10
  # 1. \A が文字列の先頭にマッチする
  # 2. 名前付きキャプチャの内側に入る
  # 3. 名前付きキャプチャ内の最初の括弧 \( に文字列の最初の ( マッチする
  # 4. \g<paren> で名前付きキャプチャ <paren> にマッチしようとする
  # 5. 上の処理の結果(?<paren>pat)に再びマッチしようとする
  # 6. \( に前から二番目の ( にマッチする
  # 7. \g<paren> でさらに (?<paren>pat) にマッチしようとするが、
  #     開き括弧 ( がもう文字列内にないので失敗する。
  #    しかし、その後ろに量指定子*があるので、0回マッチとして成功する
  # 8. 1つ目閉じ括弧 ) がマッチし、\g<paren>による再帰呼び出し全体が
  #    成功する
  # 9. 2つ目の閉じ括弧 ) が \) にマッチし、(?<paren>pat)というマッチに成功する
  # 10. 文字列の末尾へのマッチに成功する

また、パターン全体は特別に \g<0> もしくは \g'0' という記法で再帰呼び出し
できます。番号指定による呼出も可能で、\g<n> もしくは \g'n' という
記法が使えます。相対番号で部分式を指定することもでき、これは
\g<-n> \g'-n' (前側での相対位置) や
\g<+n> \g'+n' (後側での相対位置) という記法を用います。

以下の記法を用いて、
部分式呼び出しでの上のレベル、下のレベルでのマッチにアクセスすること
ができます。levelで呼出しのネストレベルを、nで位置を指定できます。
  * \k<n+level>     (n >= 1)
  * \k<n-level>     (n >= 1)
  * \k'n+level'     (n >= 1)
  * \k'n-level'     (n >= 1)
  * \k<-n+level>    (n >= 1)
  * \k<-n-level>    (n >= 1)
  * \k'-n+level'    (n >= 1)
  * \k'-n-level'    (n >= 1)
また、以下の記法で名前付きキャプチャも同様のことができます。
  * \k<name+level>
  * \k<name-level>
  * \k'name+level'
  * \k'name-level'

以下の例は回文にマッチする正規表現です。
  /\A(?<a>|.|(?:(?<b>.)\g<a>\k<b+0>))\z/.match("rekxker")
  # => #<MatchData "rekxker" a:"rekxker" b:"k">

以下の例では、開始タグと終了タグを対応付ける正規表現です。
  r = Regexp.compile(<<'__REGEXP__'.strip, Regexp::EXTENDED)
  (?<element> \g<stag> \g<content>* \g<etag> ){0}
  (?<stag> < \g<name> \s* > ){0}
  (?<name> [a-zA-Z_:]+ ){0}
  (?<content> [^<&]+ (\g<element> | [^<&]+)* ){0}
  (?<etag> </ \k<name+1> >){0}
  \g<element>
  __REGEXP__
  r.match('<foo>f<bar>bbb</bar>f</foo>').captures
  # => ["<foo>f<bar>bbb</bar>f</foo>", "<bar>", "bar", "f<bar>bbb</bar>f", "</foo>"]

最左位置での再帰呼び出しは禁止されています。
  (?<name>a|\g<name>b)   => error
  (?<name>a|b\g<name>c)  => OK

=== 選択
縦棒 | によって2つの部分正規表現のどちらか一方にマッチすれば良い
部分正規表現を記述できます。

  /\w(and|or)\w/.match("Feliformia") # => #<MatchData "form" 1:"or">
  /\w(and|or)\w/.match("furandi")    # => #<MatchData "randi" 1:"and">
  /\w(and|or)\w/.match("dissemblance") # => nil

このメタ文字は選択子(alternation operator)と呼ばれます。

=== アンカー
アンカーは幅0の文字列にマッチするメタ文字列です。
幅0とは文字と文字の間、文字列の先頭、文字列の末尾、
などを意味します。
ある特定の条件を満たす「位置」にマッチします。
  * ^ 行頭にマッチします。行頭とは、文字列の先頭もしくは改行の次を
    意味します。
  * $ 行末にマッチします。
    行末とは文字列の末尾もしくは改行の手前を意味します。
  * \A 文字列の先頭にマッチします。
  * \Z 文字列の末尾にマッチします。
    ただし文字列の最後の文字が改行ならばそれの手前にマッチします。
  * \z 文字列の末尾にマッチします。
  * \b 単語境界にマッチします。
    単語を成す文字と単語を成さない文字の間にマッチします。
    文字列の先頭の文字が単語成す文字であれば、文字列の先頭
    の位置にマッチします。
  * \B 非単語境界にマッチします。
    \bでマッチしない位置にマッチします。

  # 文字列中の real にマッチする
  /real/.match("surrealist") # => #<MatchData "real">
  # 先頭に real とないとマッチしない
  /\Areal/.match("surrealist") # => nil
  # 単語境界がrealの前にないのでマッチしない
  /\breal/.match("surrealist") # => nil
  
単語を成す文字、成さない文字の定義はエンコードによって
異なります。以下の例で「全角」括弧は EUC-JP では
単語を成す文字と見なされますが、UTF-8 では見なされません。
その結果、以下のような挙動をします。
  # -*- coding:utf-8 -*-
  # デフォルトは UTF-8
  /foo\b/.match("あいうfoo%") # => #<MatchData "foo">
  /\bfoo\b/.match("あいうfoo%") # => nil
  /\bfoo\b/e.match("（foo）".encode("EUC-JP")) # => nil
  /\bfoo\b/.match("（foo）") # => #<MatchData "foo">
Unicode の規格では、単語を成す文字を Word というプロパティで
定義しています。

==== 先読み、後読み(lookahead, lookbehind)
ある位置から続く文字列が
ある部分式にマッチするならばその位置にマッチする
という正規表現を書くことができます。

「ある位置から続く文字列(先読み、lookahead)/ある位置の手前までの文字列(後読み、lookbehind)」
と「マッチする(肯定、positive)/マッチしない(否定、negative)」
の組み合わせで4つのパターンがあります。
  * (?=pat) 肯定先読み(positive lookahead)
  * (?!pat) 否定先読み(negative lookahead)
  * (?<=pat) 肯定後読み(positive lookbehind)
  * (?<!pat) 否定後読み(negative lookbehind)

  # 以下の例では、後読みと先読みを使って <b> と
  # </b> に挟まれているという条件を正規表現中に記述しつつ
  # <b> </b> 自体にはマッチさせていない。
  /(?<=<b>)\w+(?=<\/b>)/.match("Fortune favours the <b>bold</b>")
  # => #<MatchData "bold">

===[a:option] オプション
/pat/という正規表現の直後に以下のアルファベットを
置くことで、正規表現にオプションを指定することができます。
  * /pat/i 大文字小文字を無視する
  * /pat/m メタ文字「.」が改行にマッチするようになる
  * /pat/x コメント内の空白を無視する。コメントの仕様が変化する
  * /pat/o パターン内の #{} の展開を1回限りしかしない。
i, m, x のオプションは (?on:pat) もしくは (?on-off:pat) という記法で
部分正規表現にのみ適用することができます。on、offにはi,m,xのいずれか
を置きます。onにはpatの中でのみ局所的に有効にしたいオプションを、offには
局所的に無効化したいオプションを指定します。
  /a(?i:b)c/.match("aBc") # => #<MatchData "aBc">
  /a(?i:b)c/.match("abc") # => #<MatchData "abc">
(?on) もしくは (?on-off) という形式を使うと、そこから後の
部分正規表現のみオプションを有効化することができます。
  /a(?i)bc/.match("aBc") # => #<MatchData "aBc">
  /a(?i)bc/.match("aBC") # => #<MatchData "aBC">
  # かっこの中で(?i)を指定すると、そのかっこの終わりまで有効
  /a(?:(?i)bc)d/.match("aBCd") # => #<MatchData "aBCd">
  /a(?:(?i)bc)d/.match("aBCD") # => nil

オプションは [[m:Regexp.new]] の引数に指定することもできます。
  Regexp.new("abc", Regexp::IGNORECASE)                     # => /abc/i
  Regexp.new("abc", Regexp::MULTILINE)                      # => /abc/m
  Regexp.new("abc # Comment", Regexp::EXTENDED)             # => /abc # Comment/x
  Regexp.new("abc", Regexp::IGNORECASE | Regexp::MULTILINE) # => /abc/mi


=== エンコーディング
通常、正規表現のエンコーディングはソースコードエンコーディングと
同じであると見なされます。
ただし正規表現が ascii 互換の文字しか含まない場合は 
エンコーディングは US-ASCII になります。

以下のオプションで変更することができます。
  * /pat/u UTF-8
  * /pat/e EUC-JP
  * /pat/s Windows-31J
  * /pat/n ASCII-8bit

正規表現オブジェクトのエンコーディングは [[m:Regexp#encoding]] で
取得できます。

  # -*- coding:utf-8 -*-
  /あいう/.encoding # => #<Encoding:UTF-8>
  /abc/.encoding # => #<Encoding:US-ASCII>
  /abc/u.encoding # => #<Encoding:UTF-8>

正規表現のエンコーディングと文字列のエンコーディングが非互換で
ある場合、[[c:Encoding::CompatibilityError]] が発生します。

エンコーディングについては [[d:spec/m17n]] も参考にしてください。

[[m:Regexp#fixed_encoding?]] で正規表現のエンコーディングが
「固定」さているかどうかを調べることができます。
これが真である場合には文字列とのエンコーディングが一致していないと
マッチ時に例外が発生します。
これが偽である場合にはASCII互換な文字列であればマッチの判定をさせる
ことができます。[[m:Regexp.new]] に [[m:Regexp::FIXEDENCODING]] を
指定することで明示的に指定することが可能です。
  # -*- coding:utf-8 -*-
  /あいう/.fixed_encoding? # => true
  /abc/.fixed_encoding? # => false
  /abc/e.fixed_encoding? # => true
  /abc/ =~ "あいう" # => nil
  /abc/e =~ "あいう" 
  # ~> -:6:in `<main>': incompatible encoding regexp match (EUC-JP regexp with UTF-8 string) (Encoding::CompatibilityError)


=== コメント
(?#comment here) という記法で正規表現内にコメントを書くことができます。
この記法はフリーフォーマットモードでは使えません。
かわりに # で行末までがコメントになります。

=== フリーフォーマットモード
上に説明している x オプションを使うと空白を無視するようになります。
これをフリーフォマットモード(free format mode, free spacing modeとも)
と呼びます。

フリーフォーマットモードでは # から行末まではコメント扱いされます。
  float_pat = /\A
    \d+ # 整数部
    (\. # 小数点
      \d+ # 小数部
    )?  # 小数点 + 小数部 はなくともよい
  \z/x
  float_pat.match("3.14") # => #<MatchData "3.14" 1:".14">
空白を表現したい場合はエスケープをしてください。
  /x y/x.match("x y") # => nil
  /x\ y/x.match("x y") # => #<MatchData "x y">
\s や \p{Space} のような文字クラスを使うのが良い場合も多いでしょう。

=== 一覧
Rubyで利用可能なメタ文字、メタ文字列の一覧です。

  * . 任意の1文字(改行を含まない)
文字クラス
  * [..] いずれかの1文字
  * [^..] どの文字でもない
  * && 共通部分(文字クラス内のみ)
  * x-y xからyまでの文字(文字クラス内のみ)
  * \w 単語構成文字 [a-zA-Z0-9_]
  * \W 非単語構成文字 [^a-zA-Z0-9_]
  * \s 空白文字 [ \t\r\n\f]
  * \S 非空白文字 [^ \t\r\n\f]
  * \d 10進数字 [0-9]
  * \D 非10進数字 [^0-9]
  * \h 16進数字 [0-9a-fA-F]
  * \H 非16進数字 [^0-9a-fA-F]
  * \p{property-name} Unicode プロパティ
  * \p{^property-name} \P{property-name} 否定 Unicode プロパティ
  * [:alnum:] など POSIX文字クラス (文字クラス内のみ)
繰り返し
  * * 0回以上 (greedy)
  * + 1回以上 (greedy)
  * ? 0回もしくは1回 (greedy)
  * {n} ちょうどn回(nは数字) (greedy)
  * {n,} n回以上(nは数字) (greedy)
  * {,m} m回以下(mは数字) (greedy)
  * {n,m} n回以上m回以下(n,mは数字) (greedy)
  * *? 0回以上 (reluctant)
  * +? 1回以上 (reluctant)
  * ?? 0回もしくは1回 (reluctant)
  * {n,}? n回以上(nは数字) (reluctant)
  * {,m}? m回以下(mは数字) (reluctant)
  * {n,m}? n回以上m回以下(n,mは数字) (reluctant)
  * *+ 0回以上 (possessive)
  * ++ 1回以上 (possessive)
  * ?+ 0回もしくは1回 (possessive)
キャプチャ & グループ化
  * (pat) 通常のキャプチャ&グループ化
  * \1, \2, ... キャプチャを参照
  * \k<1>, \k<2>, ... キャプチャを参照
  * \k'1', \k'2', ... キャプチャを参照
  * \k<-1>, \k<-2>, ... キャプチャを参照(相対後方参照)
  * \k'-1', \k'-2', ... キャプチャを参照(相対後方参照)
  * (?<name>pat) (?'name'pat) 名前付きキャプチャ
  * \k<name> 名前付きキャプチャを参照
  * \k'name' 名前付きキャプチャを参照
  * (?:pat) キャプチャしないグループ化
  * (?>pat) アトミックグループ化
部分式呼び出し
  * \g<name>    名前指定呼出し
  * \g'name'    名前指定呼出し
  * \g<n>       番号指定呼出し (n >= 1)
  * \g'n'       番号指定呼出し (n >= 1)
  * \g<0>       パターン全体の再帰呼び出し
  * \g'0'       パターン全体の再帰呼び出し
  * \g<-n>      相対番号指定呼出し (n >= 1)
  * \g'-n'      相対番号指定呼出し (n >= 1)
  * \g<+n>      相対番号指定呼出し (n >= 1)
  * \g'+n'      相対番号指定呼出し (n >= 1)
  * \k<n+level>     (n >= 1) ネストレベル付き後方参照
  * \k<n-level>     (n >= 1) ネストレベル付き後方参照
  * \k'n+level'     (n >= 1) ネストレベル付き後方参照
  * \k'n-level'     (n >= 1) ネストレベル付き後方参照
  * \k<-n+level>    (n >= 1) ネストレベル付き後方参照
  * \k<-n-level>    (n >= 1) ネストレベル付き後方参照
  * \k'-n+level'    (n >= 1) ネストレベル付き後方参照
  * \k'-n-level'    (n >= 1) ネストレベル付き後方参照
  * \k<name+level> ネストレベル付き後方参照
  * \k<name-level> ネストレベル付き後方参照
  * \k'name+level' ネストレベル付き後方参照
  * \k'name-level' ネストレベル付き後方参照
選択子
  * pat1|pat2 どちらか一方がマッチすれば良い
アンカー
  * ^ 行頭にマッチします。
  * $ 行末にマッチします。
  * \A 文字列の先頭にマッチします。
  * \Z 文字列の末尾にマッチします。ただし文字列の最後の文字が改行ならば
    それの手前にマッチします。
  * \z 文字列の末尾にマッチします。
  * \b 単語境界にマッチします。
  * \B 非単語境界にマッチします。
  * (?=pat) 肯定先読み
  * (?!pat) 否定先読み
  * (<=pat) 肯定後読み
  * (?<!pat) 否定後読み
条件
  * (?(cond)pat) cond が成立している場合のみ pat
  * (?(cond)truepat|falsepat) condが成立している場合は truepat 、成立していない
    場合は falsepat
オプション
  * (?on:pat) patの間だけ on オプション(i,m,x)を有効にする
  * (?on-off:pat)  patの間だけ on オプションを有効にし、offオプションを無効にする
コメント
  * (?#comment here) コメント

=== 特殊変数
パターンマッチしたときに、以下の特殊変数にマッチの情報をセットします。
  * [[m:$~]] 最後にマッチしたときの情報([[c:MatchData]] オブジェクト)
  * [[m:$&]] マッチしたテキスト全体
  * [[m:$`]] マッチしたテキストの手前の文字列
  * [[m:$']] マッチしたテキストの後ろの文字列
  * [[m:$1]], $2, ... キャプチャ文字列
  * [[m:$+]] 最後(末尾)のキャプチャ文字列
これらの変数はスレッドローカルかつメソッドでローカルな変数です。

=== 参考文献
  * 詳説正規表現(Jeffrey E. F. Friedl) 
  * Onigmoのドキュメント
  * Ruby の tarball に含まれている doc/re.rdoc or doc/regexp.rdoc
