下面就个人学习Ruby正则表达式作一个总结:

正则表达式的字面量是Regexp类型的对象。可以通过调用Regexp.new构造函数显示创建正则表达式,也可使用字面量形式

/pattern/和%r{pattern}隐式创建,%r构造体是常规分隔输入的一种形式

  1. /pattern/  
  2. /pattern/options  
  3. %r{pattern}  
  4. %r{pattern}options  
  5. Regexp.new('pattern',[, options])  

正规表达示选项(options):
   正规表达式可以包含一个或多个选项来修改模式和字符串的匹配方式,添加选项的形式如上.

   i   大小写无关   即在匹配过程中忽略模式和字符串中字符的大小写
  o   替换一次     正则表达式中的任意#...替换仅在第一次求解它的时候执行替换,否则,替换在每一次字面量生成Regexp对象时执行
  m  跨行模式     通常,'.'匹配换行符之外的任意字符,使用/m选项,"."将匹配任意字符
  x   扩展模式     x选项允许你向模式中插入空格、换行符和注释以提高它的可读性
 
   另外一组选项可以设置正则表达式的语言编码,如果没有这些选项,将使用解释器的默认编码
     n:没有编码(ASCII)   e:EUC
     s:SJIS              u:UTF-8

   一旦有了正则表达式对象,可以使用Regexp#match(stirng)或匹配操作符=~(肯定匹配)和!~(否定匹配)对字符串进行匹配匹配操作符对String和Regexp均有定义,匹配操作符至少有一个操作数必须为正则表达式

$& 得到与模式匹配的那部分字符串
$` 得到匹配之前的那部分字符串
$' 得到匹配之后的字符串
$~ 变量是MacthDate对象,保存有关匹配的所有信息

  1. def show_regexp(a, re)  
  2.   
  3.   if a=~ re  
  4.      "#{$`}<<#{$&}>>#{$'}"  
  5.   else  
  6.      "no match"  
  7.   end  
  8. end  
  9.   
  10. show_regexp('very interesting', /t/)     ->  very in<<t>>resting  
  11.   
  12. show_regexp("The ruby program", /the/)   -> no match  
  13. show_regexp("The ruby program", /the/i)  -> <<The>> ruby program  
  14. show_regexp("abc\n123", /.+/)            -> <<abc>>\n123  
  15. show_regexp("abc\n123", /.+/m)           -> <<abc\n123>>  

正则表达式模式:
   常规字符  除了 . | , [ \ ^ { + $ *  ? 外的所有字符都与它们自身相匹配,如要匹配这些特殊字符,需要在其前
             加反斜线字符(\)
   ^        匹配行首
   $        匹配行尾
   \A       匹配字符串的开始
   \z       匹配字符串的结尾
   \Z       匹配字符串的结尾,如果字符串以\n结尾,那么匹配\n前的那个字符
   \b,\B    分别匹配词边界和非词边界,组词字符可以是字母、数字和下画线

  1. show_regexp("this is\n the time", /^the/)     -> this is \n<<the>> time  
  2. show_regexp("this is\n the time", /is$/)      -> this <<is>>\nthe time  
  3. show_regexp("this is\n the time", /\Athis/)   -> <<this>> is \nthe time  
  4. show_regexp("this is\n the time", /\Athe/)    -> no match  
  5. show_regexp("this is\n the time", /\bis/)     -> this <<is>>\nthe time  
  6. show_regexp("this is\n the time", /\Bis/)     -> th<<is>> is\nthe time  


   \G       前面重复性搜索结束的位置(仅在某些情况下)
   [char]   方括号表达式匹配方号中列出的字符列表中的任意一个字符, ".|()[{+^$*?"这些字符在方括号中将失去其特殊意,此外,可以使用下面的缩写形式

 

POSIX字符类
[:alnum:] 字母和数字
[:alpha:] 大写或小写字母
[:blank:] 空格和制表符
[:cntrl:] 控制字符(至少0x00-0x1f, 0x7f)
[:digit:] 数字
[:graph:] 除了空格的可打印字符
[:lower:] 小写字符
[:print:] 任何可打印字符(包括空格)
[:punct:] 除了空格和字母数字的可打印字符
[:space:] 空格(等同于/s)
[:upper:] 大写字母
[:xdigit:] 16进制数字(0-9,a-f,A-F)
  1. show_regexp('Price $12.', [[:digit:]])         -> Price $<<1>>12  
  2. show_regexp('Price $12.', [[:punct:]aeiou])    -> Pr<<i>>ce $12  

   \d \s \w 分别匹配数字、空格和词的字符类的缩写形式, /w相当于[A-Za-z0-9]
   \D \S \W 为\d \s和\w的反义形式,分别与非数字字符,非空格字节和非词字符匹配出现在方括号外面,匹配换行符以外的任意字符(如果指定了/m选项,它也可以匹配换行符)

   下面的这种模式被称作贪心模式,因为默认情况下它们匹配尽可能多的字符串,你也可通过添加问号后缀让它们匹配最少的字符串
   re*      匹配0个或多个"re"
   re+      匹配1个或多个"re"
   re{m, n} 匹配最少m个最多n个"re"
   re{m,}   匹配最少m个"re"
   re{m}    匹配刚好m个"re"
   re?      匹配0个或1个"re",默认情况下,*,+和{m,n}都是最长匹配,在其后面加一个问号使它们执行最短匹配

  1. a= "The moon is made of cheese"  
  2. show_regexp(a, /\w+/)            -><<The>> moon is made of cheese  
  3. show_regexp(a, /\s.*\s/)         ->The<< moon is made of >>cheese  
  4. show_regexp(a, /\s.*?\s/)        ->The<< moon >>is made of cheese  
  5. show_regexp(a, /[aeiou]{2, 99}/) ->The m<<oo>>n is made of cheese  
  6. show_regexp(a, /mo?o/)           ->The <<moo>> is made of chees  

   rel|rel2   匹配"re"或者"re2",|的优先级很低
   ()             用来组合正则表达式,如/abc+/则匹配多个c,但/(abc)+/则匹配多个abc,括号也可用来收集模式匹配结果作为连续的组,在同一个模式 内,\1代表第一个组的匹配结果,\1代 表第二组匹配结果,而在模式外,殊变量$1,$2等起同样作用
  \& \` \' \+  替换整个匹配,匹配之前,匹配之后或者最高的那一组

  1. a= "red ball blue sky"  
  2. show_regexp(a, /blue|red/)           -> <<red>> ball blue sky  
  3. show_regexp(a, /red ball|angry sky/) -> <<red ball>> blue sky  

   由于|的优先级很低故最后一个匹配的是red ball或angry sky,而不会是red ball sky或red angry sky,可以通过()来改变

  1. show_regexp('banana', /an*/)    -> b<<an>>ana  
  2. show_regexp('banana', /(an)*/)  -> <<>>banana  
  3. show_regexp('banana', /(an)+/)  -> b<<anan>>a  

   使用()的组份特性  

  1. #则相当于匹配重复的组词  
  2. show_regexp('He said "Hello"', /(\w)\1/)     ->He said "He<<ll>>o"  
  3. show_regexp('Mississippi', /(\w)\1)          ->M<<ississ>>ippi  
  4. #匹配分界符  
  5. show_regexp('He said "Hello"', /(["']).*?\1/) ->He said <<"Hello">>  

   /G用在全局匹配方法String#gusb、String#gsub!、String#index 和Strng#scan中,在重复匹配中,它代表字符串内迭代中最后一具匹配结束的位置,开始时\G指向字符串开始的位置,或者String#index 方法中指定的第二个参数引用的字符

  1. "a01b23c45 d56".scan(/[a-z]\d+/)      -> ["a01""b23""c45""d56"]  
  2. "a01b23c45 d56".scan(/\G[a-z]\d+/)    -> ["a01""b23""c45"]  

   #{}      像在字符串那样,执行表达示替换。默认情况,每次求解正则表达式时都执行该替,如果设置了/o选项,那么仅在第一次求解时执行替换

正则表达式扩展:
   在ruby中所有的扩展都位于"(?"和")"之间。括起这些扩展的括号是组,但它们不生成后向引用:它们不设置\1和$1等值
   (?# comment)
       插入注释到模式中,当模式匹配时,其中的内容将被忽略
   (?:re)
       使re成为组,但不产生后向引用(即产生$1或者任何其他特殊变量)

  1. date= "12/25/01"  
  2. date=~ %r{(\d+)(/|:)(\d+)(/|:)(\d+)}  
  3. [$1$2$3$4$5]  ->   ["12""/""25""/""01"]  
  4. date=~ r{(\d+)(?:/|:)(\d+)(?:/|:)(\d+)}  
  5. [$1$2$3]          ->   ["12""25""01"]  

   (?=re)
       在此处匹配re,但并不耗用它,这不影响$&      

  1. str="red, white, and blue"  
  2. str.scan(/[a-z]+(?=,)/)    ->  ["red""withe"]  

   (?!re)
       如果此处不匹配re,则认为匹配且不消耗匹配
       如:/hot(?!dog)(\w+)/与含有字符hot且后不跟dog的词相匹配,并保存词的结尾部分到$1中
   (?>re)

       在当前锚点的第一个正规表达式中嵌套一个独立正规表达式,被其耗用的字符就不会被上层正则表达式访问,这个结构可以抑制回溯,从而提高性能

  1. str = "a" + ("b"*5000)  
  2. str =~ /^a(?>.*b).*a/     #则此匹配的模式查找性能比下面的好  
  3. str = /^a.*b.*a/  

   (?imx)
       开启i,m或者x选项,台果用在组中,则只影响该组
       (?-imx)  关闭i, m或者x选项
       (?imx:re)为re开启选项i,m或者x
       (?-imx:re)为re关闭选项i,m或者x