深入理解ES6 笔记二:模板字面量

170 阅读1分钟

ECMAScript6通过模板字面量新增了一下特性:

  • 多行字符串: 一个正式的多行字符串的概念。
  • 基本的字符串格式化: 将变量的值嵌入字符串的能力。
  • HTML转义: 向HTML插入经过安全转换后的字符串的能力。

基础语法

使用反撇号(`)包裹。如果想在字符串中使用反撇号,可以使用反斜杠(\)将其转义。

let msg = `hello`;
console.log(msg);   //  hello

let message = `\`hello\``;
console.log(message);   //  `hello`

多行字符串

直接在代码换行或显式使用'\n'指名换行

let msg = `hello
world`;
let msg1 = `hello\nworld`;
console.log(msg);   //hello
                    //world

注意:反撇号中的所有空白符都属于字符串的一部分,要小心缩进 要想通过缩进对齐文本,可通过在多行模板字面量的第一行留白,并调用trim()方法来移出最初的空行。

let html = `
<ul>
    <li>1</li>
</ul>
`.trim();

字符串占位符

占位符由一个左侧的${和右侧的}符号组成,中间可以包含任意的Javas表达式(变量、运算式、函数调用等)。

const name = 'leon',
    age = '18',
    msg = `${name} is ${age + 8} years old.`;
    
console.log(msg);   // leon is 26 years old.

值得注意的是占位符可以嵌套:

let colorList = [{color: 'blue'}, {color: 'red'}];
let html = `
<div>
  ${colorList.map((item) => {
    return `<span> ${item.color} </span>
    `;
  })}
</div>
`.trim();
console.log(html);
/*
<div>
  <span> blue </span>,<span> red </span>
</div>
*/

注意,在span标签中间多了一个逗号,这是因为当大括号中的值不是字符串时,会将其转为字符串,比如一个数组[1, 2, 3]就会被转为 1,2,3,逗号就是这样产生的。可以通过join('')来去除逗号,可以通过join('\n')来换行。

let html = `
<div>
  ${colorList.map((item) => {
    return `<span> ${item.color} </span>
    `.join('');
  })}
</div>
`.trim();

标签模板

标签值得是模板字面量第一个反撇号(`)前方标注的字符串。

const name = 'leon',
    age = '18',
    msg = tag`${name} is ${age + 8} years old.`;   // tag是模板标签

定义标签

标签可以实一个函数,调用时传入加工过的模板字面量的各部分数据,但必须结合每个部分来创建结果。第一个参数是一个数组,之后的所有参数都是每一个占位符的解释之。通过不定参数特性来定义占位符。

function tag(literals, ...substitutions) {
    console.log(literals);  // ['', ' is ', ' years old.']
    console.log(substitutions[0]); // leon
    console.log(substitutions[1]); // 18
}

利用这些参数可以把它们拼回去

function tag(literals, ...substitutions) {
    let result = '';
    
    for(let i = 0; i < substitutions.length; i++) {
        result += literals[i];
        result += substitutions[i];
    }
    
    result += literals[literals.length - 1];
    return result;
}

// 也可以这么写
function tag(literals, ...substitutions) {
    let result = '';
    
    result = substitutions.reduce((prev, next, i) => {
        return prev + substitutions[i-1] + next;
    })
    
    return result;
}

实际应用

例如可以对某些字符串进行加粗显示,在对应的位置中加入对应的样式标签。
再例如上文中为了避免 ${}表达式中返回一个数组,自动转换会导致多个逗号的问题,需要每次都将数组最后再 join('') 一下

function tag(literals, ...substitutions) {
    let result = '';
    
    for(let i = 0; i < substitutions.length; i++) {
        result += literals[i];
        let substitution = substitutions[i];
        if(Array.isArray(substitutions[i])) {
            substitution = substitutions[i].join('');
        }
        result += substitution;
    }
    
    result += literals[literals.length - 1];
    return result;
}