ES6之字符串与正则表达式的扩展

275 阅读2分钟

「这是我参与2022首次更文挑战的第2天,活动详情查看:2022首次更文挑战」。

一、字符串的扩展

1.1 unicode编码

  • 在ES6中,新增了unicode字符的表示方法 \uxxxx,其中\u代表unicode字符,xxxx是字符的码位。其中xxxx的范围是0000~ffff。
 console.log('\u0061'); // a 
  • 但是,有一些字符的表示却超出了0000-ffff的范围,比如说"𠮷"这个字,它的unicode字符\u20BB7,这时,会被Javascript理解为\u20BB+7,表示为 "₻7"。这种情况下(也就是说超出这个范围的情况下),必须用双字节表示,但是这是ES6之前的方法,ES6为我们提供了新的表示方法,那就是用大括号{}。可以表示为\u{20BB7}。这样就能被正确识别了。

  • 一个字符的6种表示,以’z‘来举例

  1. z
  2. \z 注:不能是\n这种具有特殊意义的
  3. \172 注:\HHH 三个八进制数
  4. \x7A 注:\x+两个16进制数
  5. \u007A unicode字符
  6. \u{7A} 双字节表示

1.2 字符串的遍历

ES6中新增了一种遍历字符串的方法 for of

let str ='world'

for(let item of str) {
    console.log(item) // w o r l d
}

1.3 模板字符串

1.3.1 ES5字符串的拼接

  • 首先,我们先想一想之前的字符串拼接想要换行展示需要怎么实现?
let str = '我\n'+'爱\n'+'你'

console.log(str);

上述这种实现方式是不是很麻烦,还有如下情况。这个时候a和b还不能进行运算,我们又要加上(),提高优先级才可以实现我们想要的方式

let a = 10
let b = 12

let str = '我今年'+a+b+'岁' 

console.log(str) //我今年1012岁

应该这样写

let a = 10
let b = 12

let str = '我今年'+(a+b)+'岁' 

console.log(str) //我今年22岁

为了使上述问题更简单明了,ES给我我们新的方式,模板字符串。

1.3.2 模板字符串

模板字符串用反引号表示,其中的变量我们可以用${}来表示

用模板字符串实现文字换行

let str =`我
爱
你`

console.log(str);

模板字符串表示变量

let a = 10 
let b = 12

let str = `我今年${a+b}岁`
console.log(str) //我今年22岁

嵌套模板

这种需求很常见,比如说我们根据接口的数据显示不同正确或者错误的图标,我们就可以用模板字符串来实现。多和三元表达式仪式使用。但不限于。

function isTrue() {
    return true
}

let class1 = `icon icon-${isTrue ? 'true' : 'error'}`
console.log(class1) // icon icon-true

带标签的模板字符串

其实就是模板字符串作为参数

function foo(a,b,c,d) {
    console.log(a) // ['我的名字是', ',年龄是', '岁', raw: Array(3)]
    console.log(b) //张三
    console.log(c) //26
    console.log(d) //undefined
}

let name = "张三"
let age = 26

foo`我的名字是${name},年龄是${age}岁`

其中我们可以看到,a其实是不需要被替换变量的部分组成的一个数组,其中还有raw,我们称之为原始字符串。b对应第一个变量,c对应第二个变量。不存在第三个变量,所以d为undefined

1.4 fromCodePoint

在ES5中,fromCharCode方法无法识别超出0000-ffff范围的编码。所以ES6提供了一个新的方法 fromCodePoint。这样就不会出现解析出来什么也不是这种情况了。这个方法用途并不广泛。应用场景较少。

console.log(String.fromCharCode(0x20BB7)); //ஷ
console.log(String.fromCodePoint(0x20BB7)); //𠮷

1.5 includes

在ES5中,我们常用indexof来判断字符串是否包含某元素,返回其下标或者没有时返回-1。 ES6为我们提供一种更直接的方法,判断字符串是否包含某一元素,返回值为布尔值(true||false)

console.log(str.includes('hello'))   //true
console.log(str.includes('hello1'))  // false

1.6 startsWith与endsWith

startsWith用来判断字符串是否以某元素开头,返回值是布尔值

endsWith用来判断字符串是否以某元素结尾,返回值是布尔值

let str = 'hello world'

console.log(str.startsWith('he'))   //true
console.log(str.endsWith('hello1'))  // false

1.7 repeat

字符串应重复的次数,返回一个新的字符串

let str = 'hello'

console.log(str.repeat(3)) //hellohellohello

二、正则表达式的扩展

首先我们来复习一下几个ES5的修饰符

  • i 忽略大小写
  • m 多行匹配
  • g 全局匹配

2.1 y修饰符

y修饰符,也可以称之为粘连(sticky)修饰符。其作用可以与g对比来看

let str = 'sss_ss_s'

let reg1 = /s+/g
let reg2 = /s+/y

console.log(reg1.exec(str)) //['sss', index: 0, input: 'sss_ss_s', groups: undefined]
console.log(reg2.exec(str)) //['sss', index: 0, input: 'sss_ss_s', groups: undefined]

console.log(reg1.exec(str)) //['ss', index: 4, input: 'sss_ss_s', groups: undefined]
console.log(reg2.exec(str)) //null

console.log(reg1.exec(str)) //['s', index: 7, input: 'sss_ss_s', groups: undefined]
console.log(reg2.exec(str)) //['sss', index: 0, input: 'sss_ss_s', groups: undefined]

从以上代码可以看出,g是每次从剩余的内容中进行匹配。而y是从剩余的第一个元素开始匹配,第二次开始时剩余的第一个是'_',没有匹配上,所以第三次又重头开始匹配。这是二者的区别,可以再对应场景中使用。

2.2 u修饰符

2.2.1 ES5与ES6的对比写法

u就是unicode。以前在ES5中超出0000-ffff范围的字符是无法正确处理的在正则中。如下情况 str是一个超出范围的字符,但是在ES5中这样检测却返回了true,其实这是不正确的

const str = '\uD842\uDFB7' //表示一个字符 超出了0000-ffff范围
console.log(/^\uD842/.test(str))  //true

u修饰符的出现,成功解决了这一问题

const str = '\uD842\uDFB7' //表示一个字符 超出了0000-ffff范围
console.log(/^\uD842/u.test(str))  //false

2.2.2 .修饰符的特殊情况

还有一种情况就是我们都只到'.'可以匹配换行符之外的任意字符,但在ES5中,这确实行不通的,返回的是false。u修饰符同样可以解决这一问题。

console.log(/^.$/.test(str)) //false
console.log(/^.$/u.test(str)) //true