Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/425.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript “this”在默认参数中如何工作?_Javascript_Ecmascript 6_Default Parameters - Fatal编程技术网

Javascript “this”在默认参数中如何工作?

Javascript “this”在默认参数中如何工作?,javascript,ecmascript-6,default-parameters,Javascript,Ecmascript 6,Default Parameters,所以。。。ES6ª(几小时前刚刚标准化)为函数提供了与PHP、Python等中的函数类似的默认参数。我可以这样做: function foo (bar = 'dum') { return bar; } foo(1); // 1 foo(); // 'dum' foo(undefined); // 'dum' MDN表示参数的默认值在调用时计算。这意味着每次我调用函数时,表达式'dum'都会再次求值(除非实现执行了一些我们不关心的奇怪优化) 我的问题是,这个是如何发挥作用的 let x

所以。。。ES6ª(几小时前刚刚标准化)为函数提供了与PHP、Python等中的函数类似的默认参数。我可以这样做:

function foo (bar = 'dum') {
    return bar;
}

foo(1); // 1
foo(); // 'dum'
foo(undefined); // 'dum'
MDN表示参数的默认值在调用时计算。这意味着每次我调用函数时,表达式
'dum'
都会再次求值(除非实现执行了一些我们不关心的奇怪优化)

我的问题是,
这个
是如何发挥作用的

let x = {
  foo (bar = this.foo) {
    return bar;
  }
}

let y = {
  z: x.foo
}

x.foo() === y.z(); // what?
babel transpiler当前将其评估为
false
,但我不明白。如果在通话时确实对其进行了评估,那么:

let x = 'x from global';

function bar (thing = x) {
  return thing;
}

function foo () {
  let x = 'x from foo';
  return bar();
}

bar() === foo(); // what?
function bar (thing = x) {}
{
  let x = 'x from foo';
  return bar();
}
babel transpiler目前将其评估为
true
,但我不明白。在
foo
内部调用时,为什么
bar
不从
foo
获取
x

1-是的,我知道是ES2015。
2-
3-

当他们说“在调用时进行评估”时,我认为他们指的是一个按名称调用的表达式。下面是babel如何输出第三个示例:

'use strict';

var x = 'x from global';

function bar() {
  var thing = arguments[0] === undefined ? x : arguments[0];

  return thing;
}

function foo() {
  var x = 'x from foo';
  return bar();
}

bar() === foo(); // what?
由于
var x
是在
bar
的词法范围内从全局范围继承的,这就是它的使用范围

现在,考虑以下内容:

let i = 0;

function id() {
  return i++;
}

function bar (thing = id()) {
  return thing;
}

console.info(bar() === bar()); // false
它可以传送到

"use strict";

var i = 0;

function id() {
  return i++;
}

function bar() {
  var thing = arguments[0] === undefined ? id() : arguments[0];

  return thing;
}

console.info(bar() === bar()); // false
注意这里,
id
是如何在函数内部调用的,而不是在定义函数时被缓存和记忆的,因此按名称调用而不是按值调用

因此,在第二个示例中,该行为实际上是正确的。没有
y.foo
,由于
this
在Javascript中是动态范围(即,它根据给定函数调用的接收者而变化),当
y.z()
查找
this.foo
时,它将在
y
中查找,因此
y.z()
将返回
未定义的
,而
x.foo()
将只返回
foo
函数本身

如果确实要绑定到接收器,则可以在分配时将
foo
绑定到
x
。那么它应该像预期的那样工作

抱歉,如果有任何不清楚的地方;请在评论中告诉我,我很乐意澄清!:)

我的问题是,
这个
是如何发挥作用的?我不明白。他们真的在通话时被评估了吗

是,参数初始值设定项在调用时进行计算,但基本步骤如下:

  • 在堆栈上建立一个属性,
    在被调用函数的“闭包范围”中使用
  • 如果有必要,可以
  • :
  • 将创建参数名称的可变绑定
  • 如有必要,将创建一个绑定的
    参数
    对象
  • 参数列表中的参数(包括所有分解结构等)
    在这个过程中,
  • 如果涉及任何闭包,将插入一个新环境
  • 为函数体中声明的变量创建可变绑定(如果尚未通过参数名完成),并使用
    undefined
  • 为函数体中的
    let
    const
    变量创建绑定
  • 函数的绑定(来自主体中的函数声明)是使用实例化函数初始化的
  • 最后,这是一个好消息
  • 因此,参数初始化器确实可以访问调用的
    this
    参数
    ,以及之前初始化的其他参数,以及它们的“上限”词法范围内的所有内容。它们不受函数体中声明的变量的影响(尽管它们受所有其他参数的影响,即使在它们的时间死区中也是如此)

    那么这个呢:

    let x = 'x from global';
    
    function bar (thing = x) {
      return thing;
    }
    
    function foo () {
      let x = 'x from foo';
      return bar();
    }
    
    bar() === foo(); // what?
    
    function bar (thing = x) {}
    {
      let x = 'x from foo';
      return bar();
    }
    
    我不明白。为什么调用
    bar
    时不从
    foo
    获取
    x
    内部
    foo


    因为
    x
    bar
    无权访问的局部变量。我们真幸运,他们是!参数初始化器不是在调用站点求值,而是在被调用函数的作用域内求值。在这种情况下,
    x
    标识符被解析为全局
    x
    变量。

    董事会是否宣布接受ES6最终草案?@斜视规范现场:)您的比较结果基本上是
    x.foo==y.foo
    ,这显然是
    错误的,因为在这两种情况下,您都在调用
    foo
    函数,但在第一种情况下,
    this==x
    ,在第二种情况下,
    this==y
    。问题似乎是,为什么本质上是
    让x={foo(){returnthis;};设y={z:x.foo};y、 foo()==y
    。答案是因为
    y.foo()
    与执行
    y.foo.call(y)
    相同。这就是
    这个
    的定义。“由于它在Javascript中是动态范围”,这就是我的问题所在。使用
    this.something
    不应该被特别对待,因为
    this.something
    不是魔法,只有
    this
    是魔法。我将添加一个明确的例子来澄清这个问题,谢谢你的回答!如果有人关心的话,我们在《如果你想了解更多》中对此进行了进一步讨论:)