ES6 - 基础学习(14): 函数的扩展

概述

ES6在ES5基础上对函数以及函数的应用进行了很大的扩展,虽然有些功能早就被各大浏览器广泛支持,但一直属于非标准属性 (编外人员,可怜),直到ES6才将这些写入标准 (终于转正了)。大体上包括以下几个方面:

  1、函数参数的扩展,ES6允许声明方法时给参数设置默认值,即直接写在形参定义的后面。

  2、rest参数,ES6引入了 rest参数(形如:...变量名),用于获取方法的多余参数。

  3、函数的name属性,用于获取函数的函数名。

  4、箭头函数,ES6允许使用“箭头”(=>)定义函数。

函数参数的扩展

  参数的默认值:基本用法

复制代码
// ES6允许声明方法时给参数设置默认值,即直接写在形参定义的后面。
// 既然参数在定义时就已设置默认值和数据类型,则方法里面就不需要再进行参数判定了。
function testFunc(x, y = 'ES6') {
    console.log(x, y);
}

testFunc('Welcome to');                   // Welcome to ES6
testFunc('Welcome to', 'China');          // Welcome to China
testFunc('Welcome to', '');               // Welcome to
// ES6的写法 除了代码看起来更简洁外,还有两个好处:1、阅读代码时,不用查看函数体或文档,就可以立即知道哪些参数可以省略;
// 2、有利于以后代码的优化和迭代,即使以后去掉了这个参数,也不会导致以前的代码无法运行。
复制代码
复制代码
// 在ES6之前,方法不能为参数直接指定默认值,只能通过参数判定的方式,为参数设置默认值。
// testFunc方法,在执行方法体时,先检查参数y是否有赋值(这里最好判定该参数是否有值,既不为undefined;而不是判定该参数是否为空,避免出现 空字符串、null等布尔值可以转为false的值)。若没有,则赋默认值:ES6。
function testFunc(x, y) {
    y = typeof y !== undefined ? y : 'ES6';
    console.log(x, y);
}

testFunc('Welcome to');                  // Welcome to ES6
testFunc('Welcome to', 'China');         // Welcome to China
testFunc('Welcome to', '');              // Welcome to
复制代码

   参数的默认值:使用参数默认值时,函数不允许出现同名参数

复制代码
// 不使用参数默认值时,方法内允许出现同名参数,且调用时不会报错。只是这多个同名参数实际上表示同一个参数,调用方法时,该参数以最后一个传入值为实际值。
function testFunc(x, x, y) {
    console.log(x, y);
}

testFunc(1, 2, 3);                 // 2 3

// 使用参数默认值时,则方法内不允许出现同名参数,否则调用该方法时会报错。
function test_Func(x = 1, x, y) {
    console.log(x, y);
}

test_Func(1, 2, 3);                 // Uncaught SyntaxError: Duplicate parameter name not allowed in this context
复制代码

  参数的默认值:函数参数的默认值存在暂时性死区,即在函数参数默认值表达式中,还未初始化赋值的参数无法作为其他参数的默认值。并且参数的默认值不是直接传值的,而是每次都重新计算默认值表达式的值(即参数的默认值是惰性求值)。

复制代码
function testFunc(x, y = x) {
    console.log(x, y);
}
testFunc(1);              // 1 1

// 未初始化赋值的参数无法作为其他参数的默认值
function testFunc(x = y) {
    console.log(x);
}
testFunc();              // Uncaught ReferenceError: y is not defined


// 每次都重新计算默认值表达式的值
let x = 1;
function testFunc(y = x + 1) {
    console.log(y);
}

testFunc();             // 2
x = 2;
testFunc();             // 3 每次调用函数testFunc时,都会重新计算 x + 1 的值,而不是第一次调用计算后的值
复制代码

rest参数

 ES6引入了 rest参数(形如:...变量名),用于获取方法的多余参数,从而就不需要再使用 arguments对象,查询函数的参数个数以及参数列表了。rest参数搭配的变量是一个数组,该变量将函数多余的参数放入数组中(不限长度),从而使得该函数可以传入任意多个参数。

rest参数:基本用法

function testFunc(...parList) {
    console.log(parList.length);
}

testFunc(1, 2, 3);         // 3

rest参数:与函数其他参数(固定存在的参数)混合使用

复制代码
// rest参数是一个数组,数组拥有的方法 rest参数都可以调用。
function testFunc(array, ...parList) {
    parList.forEach(function (item) {
        array.push(item);
    });
}

function test_Func(...parList) {
    console.log(parList);
}

let container = [];
testFunc(container, 1, 2, 3);
console.log(container);                // (3) [1, 2, 3]
console.log(testFunc.length);          // 1    函数参数的 length属性 只能获取函数其他参数(固定存在的参数)个数,rest参数个数,无法获取。所以不包括 rest参数。
console.log(test_Func.length);         // 0

// rest参数只能是函数最后一个参数,后面不能再跟其他参数,否则函数调用时会报错。
function test_Func(...parList, other) {
    console.log(other);
}
test_Func();                        // Uncaught SyntaxError: Rest parameter must be last formal parameter
复制代码

函数的name属性

 函数的name属性,返回该函数的函数名。这个属性早就被浏览器广泛支持,但直到 ES6,才将其写入了标准(多年的挣扎,终于转正了)。不过 ES6对 name属性的行为做了一些修改,如果将一个匿名函数赋值给一个变量,则 ES5的name属性,会返回空字符串,而 ES6的name属性则会返回实际的函数名。

复制代码
// Function构造函数返回的函数实例,name属性值为anonymous
console.log((new Function).name);        // anonymous

// bind返回的函数,name属性值会加上bound前缀。
function testFunc() {                 // 具名函数
    console.log('testFunc');
}

testFunc.bind({}).name;                  // 'bound testFunc'

(function () {                        // 匿名函数
    console.log('No name');
}).bind({}).name;                        // 'bound '
复制代码

箭头函数

ES6允许使用“箭头”(=>)定义函数,箭头函数提供了一种更加简洁的函数书写方式。基本语法:参数 => 函数体

箭头函数:基本用法

复制代码
var f = v => v;

// 等价于
var f = function(a){
    return a;
}
f(1);          //1
复制代码
复制代码
// 如果箭头函数不需要参数或需要多个参数,则使用 ()将参数部分括起来[不需要参数时,就放一个空()]。
let testFunc = () => 5;

// 等同于
let testFunc = function () {
    return 5;
};

let test_Func = (par1, par2) => par1 + par2;
// 等同于
let test_Func = function (par1, par2) {
    return par1 + par2;
};

// 如果箭头函数函数体有多行语句,则用 {}包裹起来,表示代码块;若只有一行语句,且需要返回结果时,可以省略{}, 结果会自动返回。
let test_Func = (par1, par2) => {
    return par1 + par2;
};

// 最后,如果箭头函数需要直接返回一个对象,则必须在该对象外面加上(),避免引擎将大括号认为是代码块,从而报错。
let getTempItem = id => {id: id, name:"Temp"};      // Uncaught SyntaxError: Unexpected token ':'

// 箭头函数可以与变量解构结合使用。
let testFunc = ({par1, par2}) => par1 + par2;

// 等同于
function testFunc(par) {
    return par.par1 + par.par2;
}
复制代码

箭头函数:箭头函数 + rest参数

复制代码
let format = (head, ...tail) => [head, tail];
format(1, 2, 3, 4, 5);                // [1, Array(4)]

let sum = (...nums) => {
    let tempLet = 0;
    // nums.forEach(function (item) {
    //     tempLet += item;
    // });

    for (let item of nums) {
        tempLet += item;
    }
    return tempLet;
};
let total = sum(1, 2, 3, 4, 5);        // 15

转发 https://www.cnblogs.com/donghuang/p/12423147.html
posted @ 2020-03-08 00:02  前端老鸟  阅读(150)  评论(0编辑  收藏  举报