当前位置: 代码迷 >> Web前端 >> 犀牛书札记:(13)Pattern Matching with Regular Expressions
  详细解决方案

犀牛书札记:(13)Pattern Matching with Regular Expressions

热度:470   发布时间:2012-09-21 15:47:26.0
犀牛书笔记:(13)Pattern Matching with Regular Expressions

JS类RegExp用来表示正则表达式

?

JS中正则表达式是用两个//括起来的,如

var pattern = /s$/; 等同于 var pattern = new RegExp("s$");

?

?

  • 字母数字 ? ? ? ? 本身
  • \0 ? ? ? ? ? ? ? ? ?NUL
  • \t ? ? ? ? ? ? ? ? ? Tab
  • \n ? ? ? ? ? ? ? ? ?新的一行
  • \v ? ? ? ? ? ? ? ? ?vertical tab
  • \f ? ? ? ? ? ? ? ? ? Form feed
  • \r ? ? ? ? ? ? ? ? ? carriage return
  • \xnn ? ? ? ? ? ? ? the latin character specified by the hexadecimal number nn;
  • \uxxxx ? ? ? ? ? ?the unicode character specified by the hexadecimal number xxxx;
  • \cX ? ??
这些标点在正则中有特殊的意思:
^ $ . * + ? = ! : | \ / ( ) [ ] { }
因此如果要把它们作为标点字符,需要加\,如果记不住哪些标点需要逃逸符,可以简单的在所有符号前加上逃逸符。另一方面,某些数字和字母在逃逸符前置的情况下有特殊的意义,如果仅仅只是想把逃逸符作为标点符号,也需要在前面再加一个逃逸符


Character Classes

将字符放入到[]中,就构成了一个Character Classes,Character Classes和任何包含了[]中字符的内容匹配

比如[abc]将匹配含有a,b或者c的内容。

?

相反,negated character class使用^,[^abc]将和任何不含有a,b或c的内容匹配

?

可以使用-来表示一段范围,比如[a-z],[0-9]

?

?

  • [...] ? ? ? Any one character between the brackets
  • [^...] ? ?Any one character not between the brackets.
  • . ? ? ? ? ? Any character except newline or another Unicode line terminator
  • \w ? ? ? ?Any ASCII word character. Equivalent to [a-zA-Z0-9]
  • \W ? ? ? Any character that is not an ASCII word character. Equivalent to [^a-zA-Z0-9]
  • \s ? ? ? ?Any unicode whitespace character.
  • \S ? ? ? ?Any character that is not Unicode whitespace.
  • \d ? ? ? ?Any ASCII digit. Equivalent to [0-9]
  • \D ? ? ? ?Any character other than an ASCII digit. Equivalent to [^0-9]
  • [\b] ? ? ?A literal backspace

重复

?

  • {n,m} ? ? 匹配{}之前的字符,最少出现N次,最多出现M次
  • {n,} ? ? ? 匹配之前的字符,最少出现n次
  • {n} ? ? ? ?精确出现n次
  • ? ? ? ? ? ? 0或一次出现,等同于{0,1}
  • + ? ? ? ? ? ?1或多次出现,等同于{1,}
  • * ? ? ? ? ? ?0或多次出现,等同于{0,}

以上的模式,称为贪婪重复,它将会尽可能多的匹配

如果在他们后面加上问号,比如??,+? *?就称为非贪婪匹配,它将会尽可能少的匹配,

比如,/a+/和/a+?/匹配"aaa",前者会匹配3次,而后者只匹配第一个a

?

非贪婪重复可能引起错误,比如/a*b/和/a*?b/匹配"aaab"的结果都是aaab

这是因为在正则配对中,一旦有一个字符串满足配对规则,就配对成功。也就是说,如果整个字符串满足条件,它的子字符串将不做考虑

?

|表示可选的,or的逻辑,比如/ab|cd|ef/匹配字符串ab或cd或ef

注意,用|连接的选项是从左到右进行分析的,一旦左边的条件已经满足,右边的就被忽略,即使右边的会提供一个“更好”的匹配。比如/a|ab/对于“ab",只会匹配到a

?

?

括号在正则中有多种作用:

?

  1. group separate items into a single subexpression so that the items can be treated as a single unit by |, *, +, ?, and so on.
  2. define subpatterns within the complete pattern。当某个模式成功匹配后,在得到的目标字符串中,可能只关注它的某一部分,可以使用subpattern子模式来只抽取感兴趣的部分。比如,想要匹配一个或多个小写字母后跟一个或多个数字,使用/[a-z]+\d+/,但真正关注的部分知识后面的数字,这种情况下可以使用/[a-z]+(\d+)/

?

  • ^ ? ? 匹配字符串的开头和行的开头
  • $ ? ? ?匹配字符串结尾和行尾
  • \b ? ?匹配一个单词边界。(注意不在character classes)
  • \B ? ?和非单词边界匹配
  • (?=p) ? 断言
  • (?!p) ?断言
/\bJava\b/,匹配单个单词为java的。


JS1.2支持两种标志位:

i,表示模式匹配是大小写不敏感的

g,表示模式匹配是全局的,也就是说被搜索字符串的所有匹配都会被找到

这两个标志位是在//之外的,如:

/\bjava\b/i

?

JS 1.5支持另一个标志位m,

在m模式下,如果一个被搜索字符串包含多行,^$锚点就会匹配行的开头和结尾

?

?

字符串支持4种正则操作。

?

  1. search().该方法将一个正则表达式作为参数,返回第一个匹配的子字符串的开始位置或者在无匹配情况下返回-1
    “JavaScript".search(/script/i);
    如果传入的参数不是一个正则表达式,会先将该参数传入RegExp的构造函数。search不支持全局搜索和g标志位模式
  2. replace().该方法进行一个搜索替代操作。第一个参数是一个正则表达式,第二个参数是要替换的字符串。如果该正则表达式使用g模式,该方法将替换所有匹配的子字符串,否则只替换第一个匹配。如果第一个参数是字符串,replace对待它的方式和search()相同。
    replace()的另一用法:
    var quote = /"([^"]*)"/g; 意思是:任何以"开始,后跟多个非“符号的字符,最后以”结尾的字符串
    text.replace(quote, " '$1' "); //$1指向前面正则表达式里第一个括号所匹配的内容,这句是将所有引用的字符用'符号代替"符号。
  3. match(),以一个正则表达式作为参数,返回一个数组包含匹配的结果。
    "1 plus 2 equals 3".match(/\d+/g);//returns ["1","2","3"]
    注意,如果正则表达式没有使用g模式,它将仅返回匹配的第一个元素,在这种情况下,第0个元素返回全匹配,第N个元素对应$n.比如:
    var url = /(\w+):\/\/([\w.]+)\/(\S*)/;
    var text = "Visit my blog at http://www.example.com/~david";
    var result  = text.match(url);
    
    if( result != null) {
       var fullurl = result[0]; // http://www.example.com/~david
       var protocol = result[1];//http
       var host = result[2];//www.example.com
       var path = result[3]; //~david
    }
    对于非g搜索,match还返回index属性,表明匹配的起始位置。input属性,是目标字符串的拷贝
  4. split()。
    “1,2, ? ? 3 , ? ?4 ?, 5”.split(/\s*,\s*/); //returns["1","2","3","4","5"]

?

RegExp对象

构造方法有一到两个参数,第一个是正则表达式,该表达式不用像前面那样用//包围。第二个是i,g,m标志位

RegExp对象的意义在于,由于其参数是字符串,因此可以动态的创建正则表达式

?

RegExp定义了两个方法,

?

  1. exec(),类似于match().如果找不到匹配的,返回null,如果找到一个,返回数组,也有Index,input属性。和match()不同的是,无论是不是g模式,exec()都返回相同类型的数组,每次exec()运行,都只返回一个匹配结果,并包含它的全部信息,属性lastIndex表示了该匹配最终结束的位置,如果在同一对象中多次运行exec(),后面运行的起始位置就是前面的lastIndex表示的位置。如果exec()找不到匹配,lastIndex = 0;(你也可以在某个循环中设置lastIndex=0;结束循环)
  2. test(),将一个目标字符串作为参数,如果有匹配返回true,否则返回false。test()也以lastIndex为标志,可以运行多次
RegExp对象包含5个属性
  1. source,只读字符串,表示包含的正则表达式
  2. global,只读boolean,是否是g模式
  3. ignoreCase,只读boolean,是否是i模式
  4. multiline, 只读boolean,是否是m模式
  5. lastIndex,读写证书

?

?

  相关解决方案