原文链接:https://javascript.info/regexp-quantifiers,translate with ❤️ by zhangbao.
我们有一个字符串 +7(903)-123-45-67
,想要找到里面的所有数,与查找数字不同的是,完整的数是:7,903,123,45,67
。
数是指由一或更多的数字(\d
)的组合,这个表示多少的工具称为量词。
数量 {n}
最容易理解的是花括号里的数字:{n}
。量词用来放在一个字符(或者字符类)的后面,表示需要的具体数量。
它还有高级形式,下面用例子讲:
准确的数:{5}
\d{5}
表示 5
个数字,等同于 \d\d\d\d\d
。
下面的例子查找 5 位数:
alert( "我 12345 岁了。".match(/\d{5}/) ); // "12345"
我们还可以使用 \b
去限制只查询 5 位数:\b\d{5}\b
。
从几位到几位数:{3,5}
查找 3 到 5 位数,就是在花括号里用逗号隔开表示范围的两个数:\d{3,5}
。
alert( '我不是 12 岁,我有 1234 岁了'.match(/\d{3,5}/) ); // "1234"
我们可以忽略上限数值,比如 \d{3,}
查找的是三或者更多位的数字:
alert( '我不是 12 岁,我有 345678 岁了'.match(/\d{3,}/) ); // "345678"
针对字符串 +7(903)-123-45-67
,我们需要查找数:一行里的一位或更多位数字。就用 \d{1,}
:
let str = '+7(903)-123-45-67';
let numbers = str.match(/\d{1,}/g);
alert(numbers); // 7,903,123,45,67
速记语法
经常使用的量词提供了简写形式:
+
表示”一个或者更多”,等同于 {1,}
。
例如:\d+
查找数字:
let str = '+7(903)-123-45-67';
alert( str.match(/\d+/g) ); // 7,903,123,45,67
?
表示”零或者一个”,等同于 {0,1}
。换句话说,表示字符是可选的。
例如,模式 ou?r
查找的是 o
后面跟零或者一个 u
,然后跟 r
。
所以可以查找到 color
里的 or
和 colour
里的 our
:
let str = '我是应该写成 color 还是 colour 呢?'
alert( str.match(/colou?r/g) ); // color,colour
*
表示”零或者多个”,等同于 {0,}
。表示字符可以没有,也可以重复任意次数。
下面的例子查找跟在一个数字后面的任意数量的零:
alert( '100 10 1'.match(/\d0*/g) ); // 100,10,1
与 +
(一个或者多个)进行比较:
alert( '100 10 1'.match(/\d0+/g) ); // 100,10
更多的例子
量词经常被使用,它们是复杂正则表达式的重要”构造块”。让我们看一些例子:
正则表达式”十进制小数”(浮点小数):\d+\.\d+
alert( '0 1 12.345 7890'.match(/\d+\.\d+/g) ); // 12.345
正则表达式”HTML 的开启标签,不带特性的”,像 <span>
和 <p>
:/<[a-z]+>/i
alert( '<body>...</body>'.match(/<[a-z]+>/gi) ); // <body>
我们先寻找字符”<
“,然后再找跟在后面的一位或者更多位英文字母,然后是”>
“。
正则表达式”HTML 的开启标签,不带特性的”(改进版):/<[a-z][a-z0-9]*>/i
更好的正则表达式:根据标准,HTML 标签可以在排除第一个位置之外的位置允许存在数字的,像 <h1>
。
alert( '<h1>Hi!</h1>'.match(/<[a-z][a-z0-9]*>/gi) ); // <h1>
正则表达式”开启或者关闭的 HTML 标签,不带特性的”:/<\/?[a-z][a-z0-9]*>/i
我们在标签之前加了一个可选的斜线 /?
,当然必须使用反斜线转义,否则 JavaScript 认为这是模式的结尾。
alert( '<h1>Hi!</h1>'.match(/<\/?[a-z][a-z0-9]*>/gi) ); // <h1>,</h1>
注意:更加精确意味着更加复杂
我们可以从这些例子中,看到一个共同点,正则表达式越精确——也就意味着写起来更长更复杂。
例如,HTML 标签可以用简单的正则表达式匹配:<\w+>
。
因为 \w
表示任意英文字母、数字和下划线”_
“,正则还会匹配非标签,例如 <_>
。但是比 <[a-z][a-z0-9*]>
更简单。
那我们用 <\w+>
还是 <[a-z][a-z0-9]*>
呢?
其实两者都是可以接受的。这取决实际开发时,匹配规则的宽松程度。
(完)