JS—函数概述

 1.定义

函数是对象,所以函数名就是指向函数对象的指针

(1)函数声明

        function add (n,m){
            return n+m
        }

(2)函数表达式

let add = function(n, m) { 
 return n + m; 
};

函数表达式声明和函数声明方式几乎等价

(3)箭头函数

let add = (n, m)=> { 
 return n + m; 
}

(4)Function构造函数

这个构造函数接收任意多个字符串参数,最后一个参数始终会被当成函数体,而之前的参数都是新函数的参数
let sum = new Function("num1", "num2", "return num1 + num2"); // 不推荐
不推荐使用这种语法来定义函数,因为这段代码会被解释两次:
  • 第一次是把它当作常规ECMAScript代码
  • 第二次是解释传给构造函数的字符串

这样会影响性能

2.箭头函数——ES6

任何可以使用函数表达式的地方,都可以使用箭头函数

箭头函数简洁的语法非常适合嵌入函数的场景:
1 let ints = [1, 2, 3]; 
2 console.log(ints.map(function(i) { return i + 1; })); // [2, 3, 4] 
3 console.log(ints.map((i) => { return i + 1 })); // [2, 3, 4]

箭头函数的语法:

  • 如果只有一个参数,可以省略括号,多个参数必须加括号
    • let l = e =>{ return e }
  • 如果语句只有一条return语句,则可以省略return和函数体的{}
    • let l = e => e

注意:

  • 箭头函数不能使用arguments、super、new.target
  • 也不能用作构造函数
  • 没有prototype属性

3.函数名

因为函数名就是指向函数的指针,所以它们跟其他包含对象指针的变量具有相同的行为。这意味着一个函数可以有多个名称,如下所示:
1 function sum(num1, num2) { 
2  return num1 + num2; 
3 } 
4 console.log(sum(10, 10)); // 20 
5 let anotherSum = sum; 
6 console.log(anotherSum(10, 10)); // 20 
7 sum = null; 
8 console.log(anotherSum(10, 10)); // 20 

ES6的所有函数对象都会暴露一个只读的name属性,其中包含关于函数的信息。多数情况下,这个属性种保存的就是一个函数标识符,或者说是一个字符串化的变量名。如果是使用Function构造函数创建的,会被标识为"anonymous":

1 function foo (){}
2 let bar = function(){}
3 let baz = ()=> {}
4 
5 console.log(foo.name);  // foo
6 console.log(bar.name);  // bar
7 console.log(baz.name);  // baz
8 console.log((()=>{}).name);  // 空字符串
9 console.log((new Function()).name);  // anonymous(匿名的)

如果函数是一个获取函数(getter)、设置函数(setter),或者使用bind()实例化,那么标识符前面会加上一个前缀

 1 function foo() {} 
 2 console.log(foo.bind(null).name); // bound foo 
 3 let dog = { 
 4  years: 1, 
 5  get age() { 
 6  return this.years; 
 7  }, 
 8  set age(newAge) { 
 9  this.years = newAge; 
10  } 
11 } 
12 let propertyDescriptor = Object.getOwnPropertyDescriptor(dog, ‘age‘); 
13 console.log(propertyDescriptor.get.name); // get age 
14 console.log(propertyDescriptor.set.name); // set age

4.参数

  • JS不关心传入的参数个数,也不关心参数的数据类型。
  • 主要是因为 ECMAScript 函数的参数在内部表现为一个数组。函数被调用时总会接收一个数组,但函数并不关心这个数组中包含什么。如果数组中什么也没有,那没问题;如果数组的元素超出了要求,那也没问题。
    在使用 function 关键字定义(非箭头)函数时,可以在函数内部访问 arguments 对象,从中取得传进来的每个参数值。
  • arguments 对象是一个类数组对象(但不是 Array 的实例),因此可以使用中括号语法访问其中的
    元素(第一个参数是 arguments[0],第二个参数是 arguments[1])。而要确定传进来多少个参数,
    可以访问 arguments.length 属性。

 arguments对象的值始终会与对应的参数同步:

1 function foo (n,m){
2     arguments[1] = 12
3     console.log( m );  // 12
4     console.log( arguments[1] );  // 12
5 }
6 
7 foo(1,2)

 

注意:

  • 这并不意味这两者访问同一个内存地址,只会保持同步而已
  • 如果只传了一个参数,然后把 arguments[1]设置为某个值,那么这个值并不会反映到第二个命名参数。这是因为 arguments 对象的长度是根据传入的参数个数,而非定义函数时给出的命名参数个数确定的。
    • 1 function foo (n,m){
      2     arguments[1] = 12
      3     console.log( m );  // undefined
      4     console.log( arguments[1] );  // 12
      5 }
      6 
      7 foo(1)
  • 严格模式下:
    • 给arguments[1]赋值不会影响m的值
    • 在函数种尝试重写arguments对象会导致语法错误(代码也不会执行)

(1)箭头函数中的参数

 

 

 

 

 

 

 

 

 

 

 

 

 

 

JS—函数概述

上一篇:RestSharp?.net REST/HTTP 工具库


下一篇:一台电脑安装多个版本的jdk