我试图在Javascript中学习编码并遇到了这个问题,并提出了一些问题。 results.push.bind(结果)在这个问题上做了什么?请看下面的问题:
假设getData是一个接受查询对象并返回查询结果的promise的函数。还假设someArrayOfQueries是一个查询对象数组。解释以下代码将打印的内容以及原因:
function runMultipleQueries(queries) {
var results = [];
queries.forEach(doQuery);
return results;
function doQuery(query) {
getData(query)
.then(results.push.bind(results));
}
}
function log(value) {
console.log(value);
}
runMultipleQueries(someArrayOfQueries).forEach(log);
答案 0 :(得分:0)
.push.bind做了什么?
当调用
时,返回数组的.length
function runMultipleQueries(queries) {
var results = [];
return Promise.all(queries.map(doQuery));
function doQuery(query) {
return Promise.resolve(query)
.then(results.push.bind(results))
}
}
function log(value) {
console.log(value);
}
runMultipleQueries([10, 20, 30]).then(log);
请注意,@Bergi精确地观察并警告,模式.then(results.push.bind(results))
实际上返回了数组的.length
。
仍然包含模式使用的一个解决方案是链接第二个.then()
以获取前一个.length
返回的.then()
并通过减去{{返回数组的元素1}}从值和使用括号表示法
1
虽然在使用function runMultipleQueries(queries) {
var results = [];
return Promise.all(queries.map(doQuery));
function doQuery(query) {
return Promise.resolve(query)
.then(results.push.bind(results))
.then(len => results[len - 1]);
}
}
function log(value) {
console.log(value);
}
runMultipleQueries([10, 20, 30]).then(log);
时不需要创建results
数组,但会返回值数组
Promise.all()
单独不等待.forEach()
调用的先前结果,getData()
可能是results
使用runMultipleQueries(someArrayOfQueries).forEach(log);
和Promise.all()
代替.map()
,.forEach()
return
来自Promise
来电
getData()
答案 1 :(得分:0)
在Javascript中,与其他面向对象语言不同,变量this
非常复杂,可以多次更改。
使用数组时,函数push
接受名为“on”的数组,并将一个新元素放在其末尾。在这种情况下,push函数通过读取this
变量来了解它正在处理的数组。
想象一下这个示例代码:
var myDataStructure = {};
myDataStructure.value = 0;
function addOneToValue() {
this.value += 1;
}
myDataStructure.addOne = addOneToValue;
myDataStructure.addOne(); // here - the variable `this` == myDataStructure
但是,如果您使用代码addOneToValue
调用函数addOneToValue()
,则this
的值实际上不是myDataStructure
。它未定义,或者是window
。*
要手动强制addOneToValue
始终使用myDataStructure
作为this
值,您可以执行以下操作:
addOneToValue = addOneToValue.bind(myDataStructure);
现在您可以安全地致电addOneToValue()
,因为this
值绑定到myDataStructure
。
在您的代码中,runMultipleQuery
将函数传递给另一个处理程序,该处理程序不会像results.push
那样调用函数。这意味着当调用函数时,push
将再次具有不确定的this
值。但是,通过调用bind,我们可以确保runMultipleQuery
调用push
函数并强制this
成为results
变量。
答案 2 :(得分:0)
results.push.bind(results)
的作用是强制push
的方法调用使用results
的范围。
<强> TLDR; 强>
results
是一个数组。 results.push()
是对Array#push
的调用,但是通过将函数results.push
直接传递给Promise Promise#then
,它将在不同的范围内调用。
也就是说,关键字this
将引用不同的对象。
使用bind
(例如 - https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Function/bind),范围将是&#34;绑定&#34;到特定的对象。
之所以这样,是因为JavaScript是一种原型语言,而不是面向对象的语言。