简体   繁体   English

为什么在将函数作为参数传递时我必须省略括号?

[英]Why do I have to omit parentheses when passing a function as an argument?

I am trying to wrap my head around as to why the following code results in a stack overflow when the parentheses are included, but do not when they omitted. 我试图解决为什么下面的代码在包含括号时导致堆栈溢出的原因,但是当它们被省略时则不会。

I am calling the function itself as an argument to setTimeout and it works without parantheses, but of course fails when I add them. 我将函数本身作为setTimeout的参数调用,它在没有parantheses的情况下工作,但当我添加它们时当然会失败。 It was my intuition to add the () after the function. 在函数之后添加()是我的直觉。 Just hope somebody can clear this up for me. 只希望有人可以为我解决这个问题。 When are parans optional and not? parans什么时候可选而不是?

CASE 1: 情况1:

var a = 1;

function foo() {
    a++;
    document.write(a);
    setTimeout(foo(), 2000)
}​ 
// RangeError: Maximum call stack size exceeded

CASE 2: 案例2:

var a = 1;

function foo() {
    a++;
    document.write(a);
    setTimeout(foo, 2000)
}​
// parens are omitted on foo function and it works. 

This question is usually first asked in reference to setTimeout , but I think it's important to point out that the behavior here isn't specific to that function. 这个问题通常是在引用setTimeout首先提出的,但我认为重要的是要指出这里的行为并不特定于该函数。 You simply need to understand what the parenthesis do and what it means to leave them off. 您只需要了解括号的作用以及将它们放下的含义。

Assume the following function: 假设以下功能:

function foo() {
    return 5;
}

Consider the following two variable declarations/assignments: 考虑以下两个变量声明/赋值:

var one = foo();
var two = foo;

What values do these variables have? 这些变量有什么价值?

In the first case we're executing the foo function and assigning its return value -- the number 5 -- to one . 在第一种情况下,我们执行 foo函数并将其返回值(数字5分配给one In the second case we're assigning foo itself -- more precisely, a reference to foo -- to two . 在第二种情况下,我们将foo本身 - 更准确地说是对foo的引用 - 分配给two The function is never executed. 该功能永远不会执行。

With this knowledge and an understanding that setTimeout expects as its first argument a reference to a function, it should be obvious why your first case fails, but the second one works. 有了这些知识,并且理解了setTimeout期望作为第一个参数对函数的引用 ,那么为什么你的第一个案例失败,但第二个案例失败应该是显而易见的。

Of course, your problem is exacerbated by the fact that the function you're executing is a recursive call to itself. 当然,你正在执行的函数是对自身的递归调用这一事实加剧了你的问题。 This will just run forever -- for some definition of forever -- because there's no base case to terminate the recursion. 这将永远运行 - 对于永远的某些定义 - 因为没有基本情况来终止递归。

By writing 通过写作

foo()

you're actually calling foo at that moment. 那个时候你真的在叫foo。 Which of course then calls foo() again...until you stackoverflow. 当然然后再次调用foo()...直到你stackoverflow。

In case 2 you're effectively passing a "reference" to foo, saying "run this in 2s". 在案例2中,你有效地将“引用”传递给foo,说“在2s中运行”。 Not actually calling foo(). 实际上并没有调用foo()。

So use parens when you actually want to invoke it. 因此,当您真正想要调用它时,请使用parens。 Not when you want to refer to it. 不是你想要引用它。

暂无
暂无

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

相关问题 为什么我必须使用匿名 function 而不是将附加参数传递给“setTimeout”? - Why do I have to use an anonymous function instead of passing an additional argument to `setTimeout`? 为什么“函数”的第一个参数拒绝括号? - Why does first argument of `Function` deny parentheses? 为什么传递参数时必须在addeventlistener中具有匿名函数? - Why do you have to have an anonymous function in addeventlistener when passing parameters? 为什么我们不能在数组函数参数中省略数组销毁的括号? - Why can't we omit parentheses from array destruction in array function parameters? 为什么我必须使用高阶 function 作为 setTimeout 中的第一个参数? - Why do I have to use a high order function as first argument in setTimeout? 我只需要编辑 JS object 中的一个属性,在将 object 作为参数传递给 function 时,我可以只传播所述 object 的一部分吗? - I have to edit only one property in a JS object, can I spread only a portion of a said object when passing it as an argument to a function? 为什么将 function 参数作为字符串或引用传递时,“this”会发生变化? - Why does `this` change when passing the function argument as string or reference? 为什么在 Google Script 中使用 removeLabel 函数时会收到无效参数 - Why do I get an Invalid Argument when using the removeLabel function in Google Script 为什么在我的功能中有警报时我的视图会更新,而当我没有警报时却没有更新 - Why does my view update when I have an alert in my function but doesn't when I do not 什么时候使用括号,什么时候不用? - When do I use parentheses and when do I not?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM