每周一段JavaScript权威指南-第五周

Posted by Wings on 2020-08-02

第四周

(第十章)

finish


1:第十章(正则表达式和模式匹配)

是一个描述字符模式的对象。由RegExp类表示正则表达式

1、正则表达式的定义

可以由RegExp来创建正则表达式对象,也可以直接由/RegExp/来创建字符串形式的正则表达式

0、RegExp直接量和对象的创建:
    1)程序运行时每次遇到对象直接量(初始化表达式如:{},[])的时候都会创建新对象。(如:var a = [];每次执行到这一句都会创建一个新的空数组。)
    在正则表达式中,一个直接量在执行它时会执行为一个RegExp对象。同一个正则表达式返回的都是一个新对象。

1、直接量字符:
    参照正则表达式直接字符量表

2、字符类:
    将直接量字符单独放进方括号内就组成了字符类([]有或者的含义),一个字符类可以匹配它所包含的任意字符。
    eg:/[abc]/ 就是和字母 a,b,c中的任意一个匹配就通过
    另外可以通过 ^ 字符来取非;eg:/[^abc]/ 取任意非a,b,c的字符。

3、重复:
    正则模式之后跟随 特殊字符 用以表示重复的标记。(这里注意 * 和 + 的区别)
    1)非贪婪重复:
        一般的直接添加重复字符的是贪婪匹配,他们会尽可能多的取匹配。而且允许后续的字符串继续匹配。
        而我们可以使用 ? 跟随使表达式变成非贪婪匹配。
        eg: aaa: /a+/ 匹配所有a 但是 /a+?/ 匹配 第一个a。

4、选择、分组、引用:
    1)正则表达式的语法还包括指定的选择项( | ),子表达式分组( () )和引用前一子表达式的特殊字符(  )。
    eg:字符 | 可以提供分割选择匹配 /ab|cd/ 匹配ab 或者 cd
    2)选择项的尝试匹配次序是从左到右,直到发现了匹配项。如果左边的选择项匹配,就忽略右侧。
    3)正则表达式的()有多种作用。
        1.它可以把单独的项目合成子表达式,以便像处理单独单元一样处理()里的内容。
    eg:/java(script)/ ->可以匹配到java也可以匹配到JavaScript。
        2.第二个作用是在一个完整的模式中定义子模式。当一个正则表达式成功的和目标字符串相匹配时,可以从目标串中抽出和圆括号中相匹配的部分。
        eg:'abcdefg'.replace(/(bc)d(ef)/, '$2') => "aefg" 这里的'$2'代表了(ef)也就是括号第二个匹配的内容。
        3.允许在同一个正则表达式后部以农前面的子表达式。通过在字符\后面加 (一) 或 (多个数字) 实现。这个数字表示在正则表达式中的位置。\2代表的是引用第二个带括号的位置。计数位置是根据()的左括号位置确定的
        eg:/(ab)c(de)\2/ 可以匹配到 acde 或 acdd 因为 \2是代表又写了一个(de)

5、指定匹配位置:
    1)先行断言:在符号(?=和)之间加入一个表达式。用以说明括号内的表达式必须匹配但并不是真正意义上的匹配。
    eg:/[Jj]ava([Ss]cript)?(?=\:)/ 可以匹配到Javascript: useful; 但匹配不到 Javascript。即要有:但是,如果我们用这个正则做匹配,他不会匹配出 : 这个符号。
    2)负向先行断言:(?!。用于指定接下来的字符都不必匹配。
    eg:/Java(?!Script)(A-Z\w*)/ 可以匹配Java后面跟随一个大写字母或者多个ASCII单词,但是不能匹配JavaScript/JavaScriptA。

6、修饰符:
    修饰符用于说明高级匹配模式的规则。位置在/之外。
    i:表示不区分大小写。g:表示匹配全局,所有符合的都会被匹配。m表示在多行模式中执行匹配。
    其中多行模式:^表示匹配一行的开头和字符串的开头。$表示匹配行的结束和字符串的结束。

2、用于模式匹配的String方法:

本章将讨论Sting对象的一些用以执行正则表达式模式匹配和检索替换操作的方法。
1、search方法:
    eg:JavaScript.search(/script/i) =》匹配返回值为4(根据起始位置计算)。若没有匹配则返回-
2、replace方法:replace(正则表达式/要被替换字符串,要替换的新字符串)
    用于执行检索与替换操作。
    replace的第二个参数还有可能是函数,可以动态的执行替换。该函数的返回值就是要替换成为的新值。
    这个函数有n个参数。每个参数的含义见下面例子:
1
2
3
4
5
6
'abcdefg'.replace(/(bc)d(ef)/, function(x,y,z,w,m) {
// x匹配项,第一个括号,z第二个括号,w匹配的位置, m 原始字符串
console.log(x,y,z,w,m); // bcdef bc ef 1 abcdefg
return 666
})
// "a666g"
3、match方法:他的唯一参数就是正则表达式或RegExp对象。返回一个由匹配结果组成的数组。如果有修饰符g则返回所有匹配结果。没有g则只返回第一个。余下元素则是正则表达式中用()括起来的子表达式。
eg:如果match匹配返回了一个数组a。则a[0]返回的事完整匹配。a[1]...则匹配的是第1...个括号内匹配的字符串。

4、split(正则表达式)

3、RegExp对象:

RegExp构造函数带有两个字符串参数。第一个参数包含正则表达式的主体部分。其中第二个参数是可选的,传入的是修饰符。

1、RegExp的属性:
    1)source:只读字符串,包含正则表达式的问题。
    2)global:只读bol型。用于说明是否带有修饰符 g。
    3)ignoreCase:只读bol型。用于说明是否带有修饰符 i。
    4)multiline:只读bol型。用于说明是否带有修饰符m。
    5)lastIndex:可读写证书。在 g 模式下,它存储的是下一次检索的开始位置。在exec/test方法中用到。

2、RegExp的方法:
    1)exec:对一个指定的字符串执行一个正则表达式。即对一个字符串执行匹配检索。如果他没有找到任何匹配则返回null。如果有匹配则返回一个数组。(在无g状态下)类似match。其中属性index包含了发生匹配的字符串位置。属性input引用的是正在检索的字符串。
    但是和match不同得是。不管表达式是否具有全局修饰符g。exec都会返回一样的数组。
    eg:'aabbaa'.match(/aa/) => [aa,aa]
        var a = new RegExp('aa', 'g'); a.exec('aabbaa') => ['aa']; a.lastIndex == 2;从下一次的第二个位置开始。

    2)test:和exec行为大概相同。但是返回的是bol当exec返回不为null时test返回True

总结:

1、程序每次遇到对象直接量(初始化表达式)如[],{},RegExp都会创建新对象。引用表达式则不同。
2、在正则中将字符直接量放入()内就组成了字符类。一个字符类可以匹配他所包含的任意字符。
3、重复(贪婪)尽可能多的去匹配,非贪婪尽可能少的去匹配。
4、多条件匹配是,匹配次序是从左到右找到即停止。
5、()作用:
    1)把单独项组合成子表达式,方便用特殊标示像处理独立单元一样处理他们。
    2)在完整模式中定义子模式,在match或exec匹配后可单独获取到匹配。
    3)允许在一条语句中用替代符直接引用其匹配字符。
6、零宽断言:(?=xx),匹配xx但是获取到的匹配不包括xx。
7、m修饰符:使用在 ^xyz$ 的正则表达式中匹配多行文本中 x 开头 z 结尾的字符串。
8、replace中的$number 存储的是第 Number 括号匹配的值。
9、match匹配返回一个数组,0位是匹配项,a[1,...n]是第1...n个括号的单独匹配。
10、exec:若无匹配则返回null,若有,返回数组,(在无g状态下)与match一样。
    在 g 下,他返回的总是一次匹配并把lastIndex赋值匹配位的下一次下标值。直到返回null,lastIndex归档为0.
11、test和exec的lastIndex规则一样,返回的是Boolen值。有匹配True,无匹配False