我理解以下代码:
function subtract(p1, p2) { return p1 - p2; }
function calculate(p1, p2, calculator) { return calculator(p1, p2); }
var result = calculate(2, 3, subtract); //-1
但我不明白以下有关如何将p1和p2识别为2和3的代码:
var result = calculate(2, 3, function (p1, p2) { return p1 - p2; }); //-1
答案 0 :(得分:2)
更新以解决评论:
可能我的问题不够明确。让我以另一种方式重新措辞。如果Calculate有5个参数:function calculate(p1,p2,p3,p4,calculator){return calculator(p1,p2);是否可以这样调用:var result = calculate(2,3,9,5,function(p4,p3){return p3 - p4;}); // 4不是-1我的实际问题是:参数之一如何使用其他参数作为参数,并区分哪个参数应成为哪个参数?
匿名函数知道使用p1和p2参数的原因是因为来自calculate函数定义的参数是作为计算体中的参数传递给匿名函数的参数。
也许更清楚地了解这里发生的事情的方法是更改匿名函数的函数定义中的参数名称,以便在匿名函数的函数定义中不使用这些相同的参数名称。这会产生很多混乱,并且在教授编程语言和抽象原理时经常在计算机科学教科书中有目的地完成。
除了更改匿名函数中的参数名称之外,将计算参数“calculator”更改为参数名称“fn”还可以帮助避免计算和计算器之间的混淆。考虑你的功能:
功能定义:
function calculate(p1, p2, p3, p4, fn) {
// here you can see that calculate's p1 and p2 arguments (above) are bound
// to whatever function we pass into the fn parameter.
// Whatever values p1 and p2 represent are passed into the function "fn"
// and are assigned to the parameters p1 and p2 of fn.
return fn(p1, p2);
}
函数调用计算,使用匿名函数:
我们如何知道前4个参数中的哪一个被传递到匿名函数中哪个参数未被使用?
// so here, we pass in an anonymous function that takes 2 parameters, one
//and two. We know from the definition above that whatever values are
// passed in as calculate's p1 and p2 parameters are passed into fn,
//so one and two are assigned the values 2 and 3 respectively,
// since p1 and p2 were assigned 2 and 3, and p1 and p2 were passed into
// fn in calculate's function definition above.
calculate(2, 3, 9, 5, function(one, two) {
return two - one;
});
// We know the values assigned to p1 and p2 are passed into the fn function
// as the parameters of the anonymous function known as one and two.
var result = calculate(2, 3, 9, 5, function(2, 3) {
return 3 - 2;
}
请参阅本答案顶部的计算函数定义中的return fn(p1, p2);
,以提醒您将分配给p1和p2的值传递给匿名函数的原因。
因此,匿名函数返回3 - 2 = 1。
有关此概念如何创建抽象的进一步阅读,请参阅Joel Spolsky's article - Can Your Programming Language Do This? Joel在解释为什么JavaScript如此棒的方面做得非常好!
答案 1 :(得分:0)
好function
来自calculate
并且引用名称为calculator
并且它看起来很混乱,因为计算中的 arg名称和<计算器中的strong> arg名称是相同的。
var result = calculate(2, 3, function (p1, p2) { return p1 - p2; }); //-1
现在计算函数
function calculate(p1, p2, calculator) { return calculator(p1, p2); }
args如下,
p1- 2
p2- 3
calculator - function (p1, p2) { return p1-p2; }
答案 2 :(得分:0)
计算调用它的第三个参数(计算器)作为具有自己的前两个参数p1和p2的函数。
//parameters // passing trough as arguments
function calculate(p1, p2, calculator) { return calculator(p1, p2); }
计算器可以通过它自己的p1和p2版本来计算p1和p2,这可能看起来很混乱,因为参数碰巧具有相同的名称,但它们只是被传递过来。
在您的示例中,您将传递一个本地函数进行计算,然后使用计算中的前两个参数调用该函数。
答案 3 :(得分:0)
第三个参数是(匿名)函数表达式。该表达式的结果是对新创建的可调用对象Function
实例。
calculate
函数传递2
,3
,并将该对象引用作为参数传递。 calculate
的第一个和第二个参数分别命名为p1
和p2
。第三个参数名为calculator
。因此,在calculate
中,p1
初始化为2
,p2
初始化为3
,calculator
初始化时引用了Function
以前创建的calculate
实例。
Function
然后调用引用的p1
实例,传递其p2
和2
参数3
和p1
的当前值,作为第一和第二个论点。
被调用的匿名函数有自己的名为p2
和2
的第一个和第二个参数,然后假定调用中的参数3
和{为它们传递的值{1}}。将评估引用参数的表达式,并将结果返回给其调用者,即calculate
。
calculate
然后将该值返回给其调用者。
此方法称为回调。
下次,请先使用调试器。