简要介绍一下javascript函数

前言



互联网上有很多有关此工作原理的信息,但一直以来,我几乎没有足够的文字来充分理解它。



不过,最近看来,在我看来,我还是愿意与您分享。



没有很多话



我们将介绍简单和复杂的示例-每个人都会感兴趣。



我们要注意两个要点:



(1)对于通过function(){}声明的函数,这是在调用时计算的。

(2)对于箭头函数,在创建函数时定义。



让我们从一些简单的例子开始。



function globalFunc() {
  console.log(this);
}
const globalArrowFunc = () => {
  //      ,  this - window/undefined
  //   ,   use strict   this === undefined
  console.log(this);
}

globalFunc(); // undefined
globalArrowFunc(); // undefined


如果我们将这些函数添加到对象中,该怎么办:



const cat = {
  name: 'Pirate',
  globalFunc,
  globalArrowFunc
};

cat.globalFunc(); // { name: 'Pirate', ... }
cat.globalArrowFunc(); // undefined


让我们弄清楚。



调用cat.globalFunc()返回了一个cat对象。为了便于理解,您可以这样想:“当调用通过function(){}声明的函数时,它将等于point之前的对象”。



那么为什么cat.globalArrowFunc()为我们返回未定义?事实是,箭头函数的this值是在创建时确定的,而当我们创建它时,this值是不确定的。



现在让我们用两个方法创建一个对象:



const dog = {
  name: 'Viking',
  //        
  //       
  localFunc: function() {
    console.log(this);
  },
  localArrowFunc: () => {
    console.log(this);
  }
};

dog.localFunc(); // { name: 'Viking', ... }
dog.localArrowFunc(); // undefind


这是为什么?



dog.localFunc()-因为指向狗之前的对象。

dog.localArrowFunc()-因为在对象内部这也是一个全局对象,这意味着我们不确定。



让我们的例子复杂一些。



const dog = {
  name: 'Viking',
  localFunc: function() {
    const arrowFuncInLocalFunc = () => {
      console.log(this);
    };
    function funcInLocalFunc() {
      console.log(this);
    };
    arrowFuncInLocalFunc(); // 1
    funcInLocalFunc(); // 2
  },
  localArrowFunc: () => {
    const arrowFuncInLocalArrowFunc = () => {
      console.log(this);
    };
    function funcInLocalArrowFunc() {
      console.log(this);
    };
    arrowFuncInLocalArrowFunc(); // 3
    funcInLocalArrowFunc(); // 4
  }
};

dog.localFunc();
// 1 - { name: 'Viking', ... }
// 2 - undefind
dog.localArrowFunc();
// 3 - undefind
// 4 - undefind


让我们弄清楚!



(1)arrowFuncInLocalFunc()// {name:'Viking',...}



为什么会这样?



因为创建对象时,我们将其编写为localFunc函数。而且,正如我们从前面的示例中所记得的那样,对于她来说,这是指向对象的对象,即{name:'Viking',...}。现在让我们来谈谈arrowFuncInLocalFunc函数本身-调用localFunc时会立即创建该函数,并记住其创建位置的this值。因此,我们得到了arrowFuncInLocalFunc返回我们{name:'Viking',…}。



(2)funcInLocalFunc()//未定义



为什么会发生这种情况?



如前所述,对于通过function(){}声明的函数,此值在调用时确定,并且等于point之前的对象。在这种情况下,我们在该点之前没有对象,这意味着这是一个全局对象,或者在我们的情况下是未定义的。



(3)arrowFuncInLocalArrowFunc()//未定义



为什么会这样?



此示例与(1)非常相似,仅在同一arrow函数内创建了arrowFuncInLocalArrowFunc函数。我们还记得箭头函数在声明时从其环境写入此值。但是,我们的函数是在localArrowFunc内部创建的,对此未定义。这意味着对于arrowFuncInLocalArrowFunc它将是未定义的。



(4)funcInLocalArrowFunc()//未定义



为什么会这样?



正是由于与funcInLocalFunc(2)中的原因相同,



让我们来看另一个示例:



const cat = {
  name: 'Tom',
  getFuncWithTomName: function() {
    return () => {
      console.log(this.name);
    }
  }
};

const mouse = {
  name: 'Jerry',
  logName: cat.getFuncWithTomName()
};

mouse.logName(); // Tom o_O !?


这是因为getFuncWithTomName创建并返回箭头函数,并且在创建箭头函数时,这与getFuncWithTomName相同。对于getFuncWithTomName,这是点(猫)之前的对象。





箭头函数的上下文在创建时确定。



函数(){}的上下文是在调用它们时确定的,并且它等于指向该对象之前的对象。



All Articles