一起养成写作习惯!这是我参与「掘金日新计划 · 4 月更文挑战」的第12天,点击查看活动详情。
十三、ES6+字符串方法
13-1、includes
在ES5中,如果想要查找一个字符串中是否包含另一个字符串,一般会使用indexOf、lastIndexOf、search:
- 使用indexOf()会发返回查询后第一次出现指定字符串的索引,如果未找到则返回-1
- ES6新增的includes()方法用来替代indexOf()的不足,能够更好的去判断,而不是需要根据返回的索引进一步判断
13-1-1、includes的基本使用方法
includes()方法主要用于查询字符串,判断一个字符串是否包含另一个字符串,其返回值是true / false
语法:
str.includes(searchString[, position])
参数说明:
参数 | 描述 |
---|---|
searchString | 需要查找的目标字符串 |
position | (可选)从当前字符串的哪个索引位置开始查找,默认值为0 |
const str = 'hello world';
console.log(str.includes('hello')); // true
console.log(str.includes('hello', 2)); // false
要注意的是:
当传递一个空字符串或不传递字符串时,要查询的内容会被强制转换为“undefined” ,然后再在字符串中去匹配“undefined”
'undefined'.includes(''); // true
'undefined'.includes(); // true
'123'.includes(); // false
13-1-2、includes的使用场景
includes()方法的引入是为了代替indexOf()
- includes是区分大小写的
'hello es6'.includes('hello'); // true
'hello es6'.includes('Hello'); // false
- includes传递一个参数时会从第一个字符开始查找
const str = "hello word!";
console.log(str.includes("hello")); // true
console.log(str.includes("word")); // true
console.log(str.includes("eword")); // false
- includes传递两个参数时会将第二个参数作为索引的位置开始查找(包含当前索引位置)
- 当索引为负数时,则会认为从索引为0的位置开始查找
const str = "hello word!";
console.log(str.includes("llo", 3)); // fasle
console.log(str.includes("llo", 2)); // true
console.log(str.includes("wor", 6)); // true
console.log(str.includes("ord!", -1)); // true
13-1-3、includes的注意事项
- includes会做类型转换
const str = '2022';
str.includes('2'); // true
str.includes(2); // true
- 在判断字符串2和数字2时都能返回true,是因为includes会把数字转换成字符串然后再执行查找
- 不能对Number类型直接使用
let numStr = 2020;
numStr.includes(2); // Uncaught TypeError: numStr.includes is not a function
- includes如果直接使用在数值类型上会报语法错误,所以如果想使用includes来查询就必须转换成字符串
let numStr = 2020;
(numStr+'').includes(2) // true
13-1-4、includes方法总结
- 在没有传递参数时,查询字符串会被设置成"undefined"
- includes()区分大小写
- 当有第二个参数时,会将第二个参数作为索引开始查找(包含该索引位置的字符)
- 当第二个参数为负数时,则会认为从索引为0的位置开始查找
- 如果要判断数字中有没有包含某个数字时要注意把该数字转换为字符串再去执行查找
13-2、startsWith
该方法用于判断当前字符串是否以给定字符串作为开头
- 相比includes来说,startsWith方法时间复杂度很低,因为includes方法是要对一整个字符串进行查找,比较耗费性能;而startsWith是只查找字符串的开头,而且startsWith可读性更高
- 在字符串比较短的情况下他们的效率基本没有差别,但是startsWith会更具有语义化
13-2-1、startsWith基本使用方法
startsWith()方法用于判断一个字符串是否以指定字符串为开头,如果是则返回true,否则返回false
语法:
str.startsWith(searchString[, position])
参数说明:
参数 | 描述 |
---|---|
searchString | 要搜索的子字符串 |
position | (可选)在str中搜索searchString的开始位置,默认值为0 |
const str = 'hello ES6';
console.log(str.startsWith('h')); // true
console.log(str.startsWith('h', 2)); // false
13-3、endsWith
与startsWith相反,endsWith用于判断当前字符串是否以给定子字符串为结尾
13-3-1、endsWith基本使用方法
endsWith用于判断当前字符串是否以指定字符串为结尾,如果是则返回true,否则返回false
语法:
str.endsWith(searchString[, length])
参数说明:
参数 | 描述 |
---|---|
searchString | 需要查询的子字符串 |
length | (可选)作为str的查询的长度,默认值为str.length |
const str1 = 'hello word!';
console.log(str1.endsWith('word', 10)); // true
const str2 = 'hello word!';
console.log(str2.endsWith('d')); // false
- 没有传递参数时会被当做传递了"undefined"
当字符串调用endsWith方法不传递参数时,默认是传入了“undefined”
const str = "hello";
console.log(str.endsWith()); // false
console.log(str.endsWith(undefined)); // false
const str = "undefined";
console.log(str.endsWith()); // true
console.log(str.endsWith(undefined)); // true
console.log(str.endsWith('undefined')); // true
- 当传递空字符串时会返回true(空字符串在任意字符串中都是存在的)
const str = "hello world!";
console.log(str.endsWith('')); // true
13-4、repeat
该方法用于多次拼接相同字符串,不会改变原字符串
语法:
let resultString = str.repeat(count);
参数说明:
参数 | 描述 |
---|---|
count | 介于0和正无穷大之间的整数,表示在新构造的字符串中重复了多少遍原字符串,注意count取值为负数时会报错,但是如果取值在(-1,0]之间不会报错,而是会把count当作0来处理 |
13-4-1、repeat基本使用方法
13-4-1-1、参数是小数
当参数是小数时会被取整,需要注意的是不会进行四舍五入,而是向下取整
console.log("hello".repeat(2.6)); // "hellohello"
- 这里2.6会被向下取整为2
13-4-1-2、参数是负数或Infinity
当参数是负数或Infinity时会报错
'hello'.repeat(Infinity) // RangeError
'hello'.repeat(-1) // RangeError
13-4-1-3、参数介于01或-10之间
当参数介于01或-10之间时,会被当做0来处理
console.log('hello'.repeat(0.9)); // ''
console.log('hello'.repeat(-0.9)); // ''
13-4-1-4、参数是NaN
当参数是NaN时也会被当做0
console.log('hello'.repeat(NaN)); // ''
13-4-1-5、参数是字符串
当参数是字符串时,会先转为数字,再进行repeat
console.log('hello'.repeat('two')); // ''
console.log('hello'.repeat('2')); // hellohello
console.log('hello'.repeat('2two')); // ''
- 这里two与2two转换为数字时都会变为NaN,所以结果为空字符串
13-5、padStart
该方法是在原字符串开头(左侧)填充字符串直到目标长度,并返回一个新的字符串,不会影响原字符串
语法:
str.padStart(targetLength [, padString])
参数说明:
参数 | 描述 |
---|---|
targetLength | 当前字符串需要填充到的目标长度,如果这个数值小于当前字符串本身的长度,那么将会返回字符串本身 |
padString | (可选)用于填充的字符串,如果填充的字符串超过了目标长度,则会保留最左侧的部分,其余的将会被截掉;如果不传递该参数,则默认会使用空格进行填充 |
13-5-1、padStart基本使用方法
- 拼接字符串至目标长度
console.log("word".padStart(9, 'hello')) // helloword
- 如果目标长度(参数一)小于等于字符串原本的长度,则返回原字符串
console.log("word".padStart(4, 'hello')) // word
console.log("word".padStart(3, 'hello')) // word
- 如果补全后的字符串的长度大于目标长度,则会被截取
console.log("word".padStart(8, 'hello')) // hellword
console.log("word".padStart(5, 'hello')) // hword
- 如果补全后的字符串的长度小于目标长度,那么该填充字符串会被重复填充,直至与目标长度相等(多余的字符将会被截取掉)
console.log("word".padStart(13, 'hello')) // hellohellword
console.log("word".padStart(16, 'hello')) // hellohelloheword
- 不传递第二个参数会默认使用空格进行填充
console.log("word".padStart(10)) // word
13-5-2、padStart使用场景
业务开发中,我们可以使用padStart来进行补全日期
在使用padStart前,我们可以通过以下方式实现:
function getMonth(m) {
return m < 10 ? `0${m}` : m;
}
console.log(getMonth(3)); // 03
console.log(getMonth(12)); // 12
有了padStart方法后,实现补0就很方便了:
const month = String(new Date().getMonth() + 1).padStart(2, '0');
const date = String(new Date().getDate()).padStart(2, '0');
- 目标是为了补充字符串到2位,不足两位的通过补“0”来实现
13-6、padEnd
padEnd方法用于在原字符串末尾填充指定字符串直至目标长度,返回一个新字符串,不会影响原始字符串
语法:
str.padEnd(targetLength [, padString])
参数说明:
参数 | 描述 |
---|---|
targetLength | 当前字符串需要填充到的目标长度,如果数值小于当前字符串,则会返回原字符串 |
padString | (可选)用来填充的字符串,如果填充的字符串超过了目标长度那么会进行截取,保留左侧的部分;如果不传递该参数则会默认填充空格 |
13-6-1、padEnd基本使用方法
- 拼接字符串
console.log("hello".padEnd(9, 'word')) // helloword
- 目标长度小于等于原字符串长度,则拼接不生效,返回原字符串
console.log("hello".padEnd(5, 'word')) // hello
- 补全后的字符串长度大于目标长度,则补全的字符串会被截取
console.log("hello".padEnd(6, 'word')) // hellow
- 补全后的字符串长度小于目标长度,则会重复使用补全的字符串直至到达目标长度
console.log("hello".padEnd(15, 'word')) // hellowordwordwo
- 不传递第二个参数则默认会使用空格进行补全
console.log("hello".padEnd(10)) // hello
13-6-2、padEnd使用场景
如:补充时间戳,由于数据库存储问题返回的数字为10位,此时我们可以通过padEnd来补全
let timestamp = 1634828518
timestamp = String(timestamp).padEnd(13, '0'); // 1634828518000
13-7、trim & trimStart & trimEnd
13-7-1、trim
该方法用于删除字符串两端的空格,不接受任何参数,返回一个新的字符串,不影响原本字符串
语法:
str.trim()
- 在低版本浏览器中是不支持此方法的,我们可以通过正则的方式去去除两端的空格:
if (!String.prototype.trim) {
String.prototype.trim = function () {
return this.replace(/^\s+|\s+$/gm, '');
}
}
const str1 = 'foo ';
console.log(str1.trim()); // 'foo'
const str2 = ' foo';
console.log(str2.trim()); // 'foo'
const str3 = ' foo ';
console.log(str3.trim()); // 'foo'
13-7-2、trimStart & trimEnd
除了trim外,还衍生出了trimStart与trimEnd。分别用于去除字符串开头空格、结尾空格
const str = ' hello ';
str.trim() // "hello"
str.trimStart() // "hello "
str.trimEnd() // " hello"
- 此外,trimStart与trimEnd还有别名,分别为trimLeft、trimRight
使用trimLeft与trimRight也可以达到同样的效果:
const str = ' hello ';
str.trimLeft() // "hello "
str.trimRight() // " hello"
13-8、replaceAll
13-8-1、为什么会引入replaceAll方法
由于replace方法只能替换第一个匹配的内容为指定内容,比如:
console.log('abcbcbc'.replace('b', '&')); // a&cbcbc
如果我们要替换全部内容又要使用replace方法时,只能通过正则表达式的方式去实现:
console.log('abcbcbc'.replace(/b/g, '&')); // a&c&c&c
正则表达式的方式虽能实现替换全部指定内容,但是不够直观,所以引入了replaceAll方法,可以替换所有匹配到的内容:
console.log('abcbcbc'.replaceAll('b', '&')); // a&c&c&c
13-8-2、replaceAll的基本使用方法
语法:
str.replaceAll(searchValue, replacement)
参数说明:
参数 | 描述 |
---|---|
searchValue | 表示搜索模式,可以是一个字符串,也可以是一个全局的正则表达式(必须是全局的正则表达式不然会报错) |
replacement | 要替换的内容,是一个字符串 |
- 替换指定内容
console.log('abcbcbc'.replaceAll('b', '&')); // a&c&c&c
- 传递正则表达式
- 传递正则表达式时需要注意,正则表达式的匹配模式必须是全局的,否则会报错(这点与replace方法不一样)
console.log('abcbcbc'.replaceAll(/b/, '&')); // 报错
console.log('abcbcbc'.replace(/b/, '&')); // 不报错