current position:Home>Technical part - difference between ordinary function and arrow function

Technical part - difference between ordinary function and arrow function

2021-08-27 07:26:04 Front end senior Joshua

This is my participation 8 The fourth of the yuegengwen challenge 5 God , Check out the activity details :8 Yuegengwen challenge

hello, Hello everyone , I am a Front end senior Joshua ( official account ) .
Enthusiastic about open source , Write an article . Objective to help college students , Young partners who have just entered the workplace can build their own front-end learning system as soon as possible .
If you have Confusion in learning , Welcome to follow me , Talk to me , I reply to you in real time .

First knowledge of ordinary functions and Arrow function

Usually , We're going to define a function , There are many ways .

At present, it can be roughly divided into two categories ,
One is through function Keyword to define a function , be called Ordinary function
The other is to use ES6 The syntax of the arrow function , be called Arrow function

  1. Ordinary function
//  Define a function declaratively 
function read() {
    console.log(' Front end senior Joshua')
}

//  Expression defines a function 
const read = function () {
    console.log(' Front end senior Joshua')
}
 Copy code 
  1. Arrow function
const read = () => {
    console.log(' Front end senior Joshua')
}
 Copy code 

that , We should have such a thinking , Ordinary function and What's the difference between arrow functions ?

Ordinary function and The difference between arrow functions

this Point to

Ordinary function

In ordinary functions ,this( Also known as execution time context ) The direction of is dynamic .

Dynamic execution time context , meaning this Pointing depends on how ordinary functions are called , There are four ways to call ordinary functions

below , Let's have a look

  1. Simply call ordinary functions directly , this Point to global object window, In strict mode, it's undefined
function read () {
    console.log(this)
}

read() // window
 Copy code 
  1. Ordinary functions as method properties on objects ,this Point to this object
const myObject = {
  method() {
    console.log(this);
  }
};
//  The function points to 
myObject.method(); // myObject
 Copy code 
  1. adopt bind / apply To change this Point to the ,this Point to call / apply The first parameter of
function myFunction() {
  console.log(this);
}

const myContext = { value: 'A' };

myFunction.call(myContext);  // logs { value: 'A' }
myFunction.apply(myContext); // logs { value: 'A' }
 Copy code 
  1. adopt new Keyword to call ordinary functions ( As constructor ),this Point to the constructed object instance
function MyFunction() {
  console.log(this);
}

new MyFunction(); // MyFunction Function to construct an object instance 
 Copy code 

Arrow function

In the arrow function , It does not have its own execution time context .

Arrowhead function this Is to determine the , Defined when a function is defined , Functions bound to the outer layer

No matter where the arrow function is executed , How to perform ,this Always point to the function of the outer package this

To be more precise , Arrowhead function this It points to the outer package , The closest to your ordinary function this

const myObject = {
  myMethod(items) {
    console.log(this); // logs myObject  

    const callback = () => {
      console.log(this); // logs myObject    
    };

    items.forEach(callback);
  }
};

myObject.myMethod([1, 2, 3]); 
 Copy code 

The above example : Arrow function callback() Medium this The value is equal to the external function myMethod() Of this value .

About the arrow function this, This lexical analysis , Is a major feature of arrow function .

When we use the arrow function , Remember that arrow functions don't have their own this Of , its this It's the nearest ordinary function outside this

therefore , We can avoid writing :

const self = this
 or 
callback.bind(this)
 Copy code 

About call / apply this
Contrary to ordinary functions , Use myArrowFunc.call(thisVal) or myArrowFunc.apply(thisVal) Calling the arrow function indirectly does not change this Value : Context values are always parsed lexically .

however , If it is an arrow function defined globally , this Point to window

var read = () => {
    console.log(this)
}

var obj = {
    read: read
}

obj.read() // window
 Copy code 

Constructors

Ordinary function

Through ordinary functions , You can easily construct an object instance

function Car(color) {
  this.color = color;
}

const redCar = new Car('red');
redCar instanceof Car; // => true
 Copy code 

Car It's a normal function , Use new Keyword when calling this function , There will be one Car The object instance of is created

Arrow function

because this The result of lexical analysis , Arrow functions cannot be used as constructors .

If you try to call to new Arrow function with keyword prefix ,JavaScript Will throw an error :

const Car = (color) => {
  this.color = color;
};

const redCar = new Car('red'); // TypeError: Car is not a constructor 
 Copy code 

call new Car('red'), among Car It's an arrow function , Will throw out TypeError: Car is not a constructor.

arguments object

Ordinary function

In normal functions , keyword arguments Is a class array object , It is a series of parameters passed during function execution

function myFunction() {
  console.log(arguments);}

myFunction('a', 'b'); // logs { 0: 'a', 1: 'b', length: 2 }
 Copy code 

stay myFunction() Inside , Parameter is an array like object , It contains call parameters :'a' and 'b'.

Arrow function

Arrow function , It's not arguments keyword .

And this identical ,arguments Lexical analysis of keywords : The arrow function accesses... From an external function arguments.
That is to say , this / arguments Always point to the function of the outer package this / arguments

function outer() {
  const inner = () => {    
      console.log(arguments);  
    }
  inner('c', 'd');
}

outer('a', 'b'); // logs { 0: 'a', 1: 'b', length: 2 }
 Copy code 

We can see , Arrow function inner, Parameters were passed during execution - 'c', 'd'. But the arrow function inner When printing internally , Is a function that prints an external outer Of arguments

doubt , So if the arrow function Hope like Ordinary functions get arguemts Keyword as a convenient way to obtain parameters , What to do ?

Good idea , We can use ... The operator

function myRegularFunction() {
  const myArrowFunction = (...args) => {    
      console.log(args);  
    }
  myArrowFunction('c', 'd');
}

myRegularFunction('a', 'b'); // logs ['c', 'd']
 Copy code 

When executing the arrow function ,...args Is to collect the parameters of the arrow function --- ['c', 'd']

Invisible return

Ordinary function

In normal functions , Yes return XXX Just go back to XXX
If it is return perhaps It's not return, Is to return to undefined

function myFunction() {
  return 42;
}

function myEmptyFunction() {
  42;
}

function myEmptyFunction2() {
  42;
  return;
}

myFunction(); // => 42
myEmptyFunction();  // => undefined
myEmptyFunction2(); // => undefined
 Copy code 

Arrow function

In the arrow function , You can do the same return operation as ordinary functions , But there is a simple way to use it , No need to use return Keyword can also return the value we need

If the arrow function just contains an expression , And you omit the curly braces for the function , The expression will be implicitly returned . These are inline arrow functions .

const increment = (num) => num + 1;

increment(41); // => 42
 Copy code 

increment() The arrow contains only one expression :num + 1. This expression is implicitly returned by the arrow function , Not used return keyword .

stay class Method properties in

stay class in this Execution issues

  1. Ordinary function
    Use ordinary functions as method properties :
class Hero {
  constructor(heroName) {
    this.heroName = heroName;
  }

  logName() {    console.log(this.heroName);  }}

const batman = new Hero('Batman');
 Copy code 

Sometimes , I need to use batman.logName Callback function , For example Event callback Or is it setTimeout() The callback , So at this point , There will be a little problem

setTimeout(batman.logName, 1000);
// after 1 second logs "undefined"
 Copy code 

There's a solution ? Yes , Can pass call / apply To change this Point to

setTimeout(batman.logName.bind(batman), 1000);
// after 1 second logs "Batman"
 Copy code 

however , If there is more code , There will be a lot of boilerplate code , Reading ability is not high

A better way is , stay class Use the arrow function

2, Arrow function

class Hero {
  constructor(heroName) {
    this.heroName = heroName;
  }

  logName = () => {    console.log(this.heroName);  }}

const batman = new Hero('Batman');

setTimeout(batman.logName, 1000);
// after 1 second logs "Batman"
 Copy code 

Now? , Compared with ordinary functions , Use the method defined by the arrow to this Points to a class instance .

Of course , You may think as much as I do , Arrowhead function this How does it bind to class instances ?
We go through babel Compiled :

"use strict";

function _defineProperty(obj, key, value) {
  if (key in obj) {
    Object.defineProperty(obj, key, {
      value: value,
      enumerable: true,
      configurable: true,
      writable: true
    });
  } else {
    obj[key] = value;
  }
  return obj;
}

class Hero {
  constructor(heroName) {
    _defineProperty(this, "logName", () => {
      console.log(this.heroName);
    });

    this.heroName = heroName;
  }
}

const batman = new Hero("Batman");
 Copy code 

Essentially , It's through Object.defineProperty take class Of this and logName Function to bind . And for ordinary functions , Is not going to this and Binding to ordinary objects .

summary

  1. this Point to : In normal functions , Is dynamic , Function dependent calls ; In the arrow function , Because syntax parsing ,this The point is certain ,this Is bound to the outer function , If it's the outermost layer, there's no function window
  2. arguments: In normal functions , You can get all the parameters ; In the arrow function ,arguments Is a function pointing to the outer layer arguments Of . If you want to get the parameters of the unified arrow function , have access to The operator
  3. return: If the arrow function has only one expression , This expression will be implicitly returned , And you don't need to use return keyword
  4. We can do it in class Use the arrow function ,this Will bind to class instances

These are ordinary functions And The difference between arrow functions , Hope to useful

Move your hands

  • Welcome to follow me GitHub:@huangyangquang
  • Welcome to my official account. : Front end senior Joshua

copyright notice
author[Front end senior Joshua],Please bring the original link to reprint, thank you.
https://en.qdmana.com/2021/08/20210827072600363h.html

Random recommended