繁体   English   中英

为什么带有“ this”的此功能不起作用? 关于“这个”及其范围

[英]Why does this function with “this” not work? About “this” and its scope

我知道以这种方式向原型添加方法并不是最好的方法,但是我只是在测试。

 Array.prototype.maap = function (transform) { let mapped = []; for (let element of this) { mapped.push(transform(element)); } return mapped; } console.log([0, 2, 3].maap(n => n / this.length)); 

我正进入(状态:

[NaN,Infinity,Infinity]。 我认为问题是“ this.length”。

没错,问题是this.length 麻烦的是它不在函数中 它在lambda中,其作用域不是后来被其调用的数组的作用域。 因此, this不是数组,而this.length是实数0(0/0为NaN,2/0为无穷大,而3/0也为无穷大)。

您可以对实际值3进行硬编码,也可以将逻辑移入函数本身。 或者,您可以让lambda(实际上是JavaScript中的“箭头函数”)采用另一个参数:分母的参数。

 Array.prototype.maap = function (transform) { let mapped = []; for (let element of this) { mapped.push(transform(element, this.length)); } return mapped; } console.log([0, 2, 3].maap((n, m) => n / m)); 

this箭头函数内部引用相同的this在其包含块。 在这里,包含块是顶层, this是指windowwindow.length0

 console.log(this === window); console.log(window.length); 

因此,您的代码等效于:

 Array.prototype.maap = function(transform) { let mapped = []; for (let element of this) { mapped.push(transform(element)); } return mapped; } console.log(this.length); console.log([0, 2, 3].maap(n => n / 0)); 

0 / 0undefined ,而大多数其他数字/ 0Infinity (或-Infinity )。

如果要使用this模拟Array.prototype.map的行为,则传递给maap的第二个参数应该是使用this方法调用回调的this值:

 Array.prototype.maap = function(transform, thisVal) { let mapped = []; for (let element of this) { mapped.push(transform.call(thisVal, element)); } return mapped; } const arr = [0, 2, 3]; console.log(arr.maap( function(n){ return n / this.length; }, arr )); 

我认为问题出在箭头函数(参数transform )上,是的, this.length是直接相关的问题,深入一点,这是关于箭头函数的问题,

箭头函数没有它自己的this 使用封闭词汇范围的this值;

简而言之,其中箭头功能定义了this点的位置。

因此,对于您的代码,您传入的参数为n => n / this.length ,并且在window环境中的console.log函数中定义。 所以真正的问题是:

transf = (n) => {
  console.log(this);    // Window {postMessage: ƒ, blur: ƒ, focus: ƒ, close: ƒ, parent: Window, …}
  return n / this.length
}
console.log([0, 2, 3].maap(transf));

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM