Heim  >  Artikel  >  Web-Frontend  >  Was ist der Unterschied zwischen Pfeilfunktionen und gewöhnlichen Funktionen in es6?

Was ist der Unterschied zwischen Pfeilfunktionen und gewöhnlichen Funktionen in es6?

青灯夜游
青灯夜游Original
2022-03-08 12:11:013899Durchsuche

Unterschiede: 1. Die Definition der Pfeilfunktion ist viel einfacher, klarer und schneller als die Definition einer gewöhnlichen Funktion. 2. Die Pfeilfunktion erstellt keine eigene Funktion, die gewöhnliche Funktion jedoch nicht als Konstruktor verwendet werden. 4. Die Pfeilfunktion hat keine eigenen Argumente, die Pfeilfunktion jedoch.

Was ist der Unterschied zwischen Pfeilfunktionen und gewöhnlichen Funktionen in es6?

Die Betriebsumgebung dieses Tutorials: Windows 7-System, ECMAScript Version 6, Dell G3-Computer.

Die Pfeilfunktion ist ein hochfrequenter Testpunkt in Front-End-Interviews. Ich glaube, viele Leute wissen, dass ihre Syntax einfacher ist als bei gewöhnlichen Funktionen.

1. Grundlegende Syntax

ES6 ermöglicht die Verwendung von Pfeilen => zum Definieren von Pfeilfunktionen. Schauen wir uns für die spezifische Syntax ein einfaches Beispiel an: =>来定义箭头函数,具体语法,我们来看一个简单的例子:

// 箭头函数
let fun = (name) => {
    // 函数体
    return `Hello ${name} !`;
};

// 等同于
let fun = function (name) {
    // 函数体
    return `Hello ${name} !`;
};

可以看出,定义箭头函在数语法上要比普通函数简洁得多。箭头函数省去了function关键字,采用箭头=>来定义函数。函数的参数放在=>前面的括号中,函数体跟在=>后的花括号中。

关于箭头函数的参数:

如果箭头函数没有参数,直接写一个空括号即可。

如果箭头函数的参数只有一个,也可以省去包裹参数的括号。

如果箭头函数有多个参数,将参数依次用逗号(,)分隔,包裹在括号中即可。

// 没有参数
let fun1 = () => {
    console.log(111);
};

// 只有一个参数,可以省去参数括号
let fun2 = name => {
    console.log(`Hello ${name} !`)
};

// 有多个参数
let fun3 = (val1, val2, val3) => {
    return [val1, val2, val3];
};

关于箭头函数的函数体:

如果箭头函数的函数体只有一句代码,就是简单返回某个变量或者返回一个简单的JS表达式,可以省去函数体的大括号{ }。

let f = val => val;
// 等同于
let f = function (val) { return val };

let sum = (num1, num2) => num1 + num2;
// 等同于
let sum = function(num1, num2) {
  return num1 + num2;
};

如果箭头函数的函数体只有一句代码,就是返回一个对象,可以像下面这样写:

// 用小括号包裹要返回的对象,不报错
let getTempItem = id => ({ id: id, name: "Temp" });

// 但绝不能这样写,会报错。
// 因为对象的大括号会被解释为函数体的大括号
let getTempItem = id => { id: id, name: "Temp" };

如果箭头函数的函数体只有一条语句并且不需要返回值(最常见是调用一个函数),可以给这条语句前面加一个void关键字

let fn = () => void doesNotReturn();

箭头函数最常见的用处就是简化回调函数。

// 例子一
// 正常函数写法
[1,2,3].map(function (x) {
  return x * x;
});

// 箭头函数写法
[1,2,3].map(x => x * x);

// 例子二
// 正常函数写法
var result = [2, 5, 1, 4, 3].sort(function (a, b) {
  return a - b;
});

// 箭头函数写法
var result = [2, 5, 1, 4, 3].sort((a, b) => a - b);

二、箭头函数与普通函数的区别

1、语法更加简洁、清晰

从上面的基本语法示例中可以看出,箭头函数的定义要比普通函数定义简洁、清晰得多,很快捷。

2、箭头函数不会创建自己的this(重要!!深入理解!!)

我们先来看看MDN上对箭头函数this的解释。

箭头函数不会创建自己的this,所以它没有自己的this,它只会从自己的作用域链的上一层继承this

箭头函数没有自己的this,它会捕获自己在定义时(注意,是定义时,不是调用时)所处的外层执行环境的this,并继承这个this值。所以,箭头函数中this的指向在它被定义的时候就已经确定了,之后永远不会改变。

来看个例子:

var id = 'Global';

function fun1() {
    // setTimeout中使用普通函数
    setTimeout(function(){
        console.log(this.id);
    }, 2000);
}

function fun2() {
    // setTimeout中使用箭头函数
    setTimeout(() => {
        console.log(this.id);
    }, 2000)
}

fun1.call({id: 'Obj'});     // 'Global'

fun2.call({id: 'Obj'});     // 'Obj'

上面这个例子,函数fun1中的setTimeout中使用普通函数,2秒后函数执行时,这时函数其实是在全局作用域执行的,所以this指向Window对象,this.id就指向全局变量id,所以输出'Global'。 但是函数fun2中的setTimeout中使用的是箭头函数,这个箭头函数的this在定义时就确定了,它继承了它外层fun2的执行环境中的this,而fun2调用时thiscall方法改变到了对象{id: 'Obj'}中,所以输出'Obj'

再来看另一个例子:

var id = 'GLOBAL';
var obj = {
  id: 'OBJ',
  a: function(){
    console.log(this.id);
  },
  b: () => {
    console.log(this.id);
  }
};

obj.a();    // 'OBJ'
obj.b();    // 'GLOBAL'

上面这个例子,对象obj的方法a使用普通函数定义的,普通函数作为对象的方法调用时,this指向它所属的对象。所以,this.id就是obj.id,所以输出'OBJ'。 但是方法b是使用箭头函数定义的,箭头函数中的this实际是继承的它定义时所处的全局执行环境中的this,所以指向Window对象,所以输出'GLOBAL'。(这里要注意,定义对象的大括号{}

var id = 'Global';
// 箭头函数定义在全局作用域
let fun1 = () => {
    console.log(this.id)
};

fun1();     // 'Global'
// this的指向不会改变,永远指向Window对象
fun1.call({id: 'Obj'});     // 'Global'
fun1.apply({id: 'Obj'});    // 'Global'
fun1.bind({id: 'Obj'})();   // 'Global'
Wie Sie Wie Sie sehen, ist das Definieren von Pfeilfunktionen in Bezug auf die mathematische Syntax viel einfacher als gewöhnliche Funktionen. Die Pfeilfunktion lässt das Schlüsselwort function weg und verwendet den Pfeil =>, um die Funktion zu definieren. Die Parameter der Funktion stehen in den Klammern vor => und der Funktionskörper steht in den geschweiften Klammern nach =>.

🎜🎜Über die Parameter der Pfeilfunktion: 🎜🎜🎜🎜①🎜 Wenn die Pfeilfunktion keine Parameter hat, schreiben Sie einfach eine leere Klammer. 🎜🎜🎜②🎜 Wenn die Pfeilfunktion nur einen Parameter hat, können Sie die Klammern rund um den Parameter auch weglassen. 🎜🎜🎜③🎜 Wenn die Pfeilfunktion mehrere Parameter hat, trennen Sie die Parameter durch Kommas (,) und schließen Sie sie in Klammern ein. 🎜
let Fun = (name, age) => {
    this.name = name;
    this.age = age;
};

// 报错
let p = new Fun('cao', 24);
🎜🎜Über den Funktionskörper der Pfeilfunktion: 🎜🎜🎜🎜①🎜 Wenn der Funktionskörper der Pfeilfunktion nur eine Codezeile enthält, die einfach eine Variable oder einen einfachen JS-Ausdruck zurückgibt, werden die geschweiften Klammern der Der Funktionskörper kann weggelassen werden. 🎜
// 例子一
let fun = (val) => {
    console.log(val);   // 111
    // 下面一行会报错
    // Uncaught ReferenceError: arguments is not defined
    // 因为外层全局环境没有arguments对象
    console.log(arguments); 
};
fun(111);

// 例子二
function outer(val1, val2) {
    let argOut = arguments;
    console.log(argOut);    // ①
    let fun = () => {
        let argIn = arguments;
        console.log(argIn);     // ②
        console.log(argOut === argIn);  // ③
    };
    fun();
}
outer(111, 222);
🎜🎜②🎜 Wenn der Funktionskörper der Pfeilfunktion nur eine Anweisung hat, nämlich ein Objekt zurückzugeben, können Sie es so schreiben: 🎜
let sayHi = () => {
    console.log('Hello World !')
};
console.log(sayHi.prototype); // undefined
🎜🎜③🎜 Wenn der Funktionskörper der Pfeilfunktion nur eine hat Anweisung und muss keinen Wert zurückgeben (am häufigsten wird der Aufruf einer Funktion verwendet). Sie können vor dieser Anweisung ein Schlüsselwort void hinzufügen🎜rrreee🎜Pfeilfunktionen werden am häufigsten verwendet Vereinfachen Sie die Rückruffunktion. 🎜rrreee🎜🎜🎜 2. Der Unterschied zwischen Pfeilfunktionen und gewöhnlichen Funktionen 🎜🎜🎜🎜🎜 1. Die Syntax ist prägnanter und klarer 🎜🎜🎜 Wie aus den grundlegenden Syntaxbeispielen oben ersichtlich ist, ist die Definition von Pfeilfunktionen einfacher als die Definition gewöhnlicher Funktionen, viel klarer und schneller. 🎜🎜🎜2. Die Pfeilfunktion erstellt kein eigenes This (Wichtig!! Tiefes Verständnis!!) 🎜🎜🎜 Schauen wir uns zunächst die Erklärung der Pfeilfunktion this auf MDN an . 🎜🎜🎜Die Pfeilfunktion erstellt kein eigenes this, daher hat sie kein eigenes this, sie erbt nur von der oberen Ebene ihrer eigenen Bereichskette this. 🎜🎜🎜Die Pfeilfunktion verfügt nicht über einen eigenen this, sie erfasst den this der 🎜äußeren Ausführungsumgebung, wo er sich bei 🎜Definition🎜 befindet (beachten Sie, wenn er definiert ist, nicht). wenn es aufgerufen wird) 🎜 und diesen diesen-Wert erben. Daher wird die Ausrichtung von this in der Pfeilfunktion bei der Definition festgelegt und wird sich später nie ändern. 🎜🎜Schauen wir uns ein Beispiel an: 🎜rrreee🎜Im obigen Beispiel wird eine normale Funktion in setTimeout in der Funktion fun1 verwendet, wenn die Funktion nach 2 ausgeführt wird Sekunden wird die Funktion tatsächlich im globalen Bereich ausgeführt, sodass this auf das Window-Objekt und this.id auf das Objekt zeigt globale Variable id Geben Sie also 'Global' aus. Die Pfeilfunktion wird jedoch in setTimeout in der Funktion fun2 verwendet. Der this dieser Pfeilfunktion wird bei der Definition bestimmt und erbt ihn . this in der Ausführungsumgebung des äußeren fun2, und wenn fun2 aufgerufen wird, ist this aufgerufen Die Code>-Methode wird in das Objekt <code>{id: 'Obj' geändert, sodass 'Obj' ausgegeben wird. 🎜🎜Sehen wir uns ein weiteres Beispiel an: 🎜rrreee🎜Im obigen Beispiel wird die Methode a des Objekts obj mithilfe einer gewöhnlichen Funktion definiert. 🎜Wenn die gewöhnliche Funktion ist this wird als Methode des Objekts aufgerufen und zeigt auf das Objekt, zu dem es gehört 🎜. Daher ist this.id obj.id, sodass 'OBJ' ausgegeben wird. Die Methode b wird jedoch mithilfe einer Pfeilfunktion this in der Pfeilfunktion definiert und erbt tatsächlich thisin der globalen Ausführungsumgebung, in der sie definiert ist >, also zeigt es auf das Window-Objekt, also wird 'GLOBAL' ausgegeben. (🎜Hier ist zu beachten, dass die geschweiften Klammern {}, die das Objekt definieren, keine separate Ausführungsumgebung bilden können, es befindet sich immer noch in der globalen Ausführungsumgebung!!🎜)🎜

3、箭头函数继承而来的this指向永远不变(重要!!深入理解!!)

上面的例子,就完全可以说明箭头函数继承而来的this指向永远不变。对象obj的方法b是使用箭头函数定义的,这个函数中的this永远指向它定义时所处的全局执行环境中的this,即便这个函数是作为对象obj的方法调用,this依旧指向Window对象。

4、.call()/.apply()/.bind()无法改变箭头函数中this的指向

.call()/.apply()/.bind()方法可以用来动态修改函数执行时this的指向,但由于箭头函数的this定义时就已经确定且永远不会改变。所以使用这些方法永远也改变不了箭头函数this的指向,虽然这么做代码不会报错。

var id = &#39;Global&#39;;
// 箭头函数定义在全局作用域
let fun1 = () => {
    console.log(this.id)
};

fun1();     // &#39;Global&#39;
// this的指向不会改变,永远指向Window对象
fun1.call({id: &#39;Obj&#39;});     // &#39;Global&#39;
fun1.apply({id: &#39;Obj&#39;});    // &#39;Global&#39;
fun1.bind({id: &#39;Obj&#39;})();   // &#39;Global&#39;

5、箭头函数不能作为构造函数使用

我们先了解一下构造函数的new都做了些什么?简单来说,分为四步: ① JS内部首先会先生成一个对象; ② 再把函数中的this指向该对象; ③ 然后执行构造函数中的语句; ④ 最终返回该对象实例。

但是!!因为箭头函数没有自己的this,它的this其实是继承了外层执行环境中的this,且this指向永远不会随在哪里调用、被谁调用而改变,所以箭头函数不能作为构造函数使用,或者说构造函数不能定义成箭头函数,否则用new调用时会报错!

let Fun = (name, age) => {
    this.name = name;
    this.age = age;
};

// 报错
let p = new Fun(&#39;cao&#39;, 24);

6、箭头函数没有自己的arguments

箭头函数没有自己的arguments对象。在箭头函数中访问arguments实际上获得的是外层局部(函数)执行环境中的值。

// 例子一
let fun = (val) => {
    console.log(val);   // 111
    // 下面一行会报错
    // Uncaught ReferenceError: arguments is not defined
    // 因为外层全局环境没有arguments对象
    console.log(arguments); 
};
fun(111);

// 例子二
function outer(val1, val2) {
    let argOut = arguments;
    console.log(argOut);    // ①
    let fun = () => {
        let argIn = arguments;
        console.log(argIn);     // ②
        console.log(argOut === argIn);  // ③
    };
    fun();
}
outer(111, 222);

上面例子二,①②③处的输出结果如下:

Was ist der Unterschied zwischen Pfeilfunktionen und gewöhnlichen Funktionen in es6?

很明显,普通函数outer内部的箭头函数fun中的arguments对象,其实是沿作用域链向上访问的外层outer函数的arguments对象。

可以在箭头函数中使用rest参数代替arguments对象,来访问箭头函数的参数列表!!

7、箭头函数没有原型prototype

let sayHi = () => {
    console.log(&#39;Hello World !&#39;)
};
console.log(sayHi.prototype); // undefined

8、箭头函数不能用作Generator函数,不能使用yeild关键字

【相关推荐:javascript视频教程web前端

Das obige ist der detaillierte Inhalt vonWas ist der Unterschied zwischen Pfeilfunktionen und gewöhnlichen Funktionen in es6?. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!

Stellungnahme:
Der Inhalt dieses Artikels wird freiwillig von Internetnutzern beigesteuert und das Urheberrecht liegt beim ursprünglichen Autor. Diese Website übernimmt keine entsprechende rechtliche Verantwortung. Wenn Sie Inhalte finden, bei denen der Verdacht eines Plagiats oder einer Rechtsverletzung besteht, wenden Sie sich bitte an admin@php.cn