Javascript-为什么这段代码会阻塞?
我不明白为什么这个代码会阻塞。我使用nodejs异步函数,但现在我试图弄清楚非阻塞编程的本质是什么,以及如何实现它们。 这是我想的方式,但它仍然阻塞Javascript-为什么这段代码会阻塞?,javascript,node.js,Javascript,Node.js,我不明白为什么这个代码会阻塞。我使用nodejs异步函数,但现在我试图弄清楚非阻塞编程的本质是什么,以及如何实现它们。 这是我想的方式,但它仍然阻塞 var async_func = function(x, func) { func(x+5); }; setTimeout( async_func(5, function(number) { for (var x = 0; x < 1000000000; x++) {;}
var async_func = function(x, func) {
func(x+5);
};
setTimeout( async_func(5, function(number) {
for (var x = 0; x < 1000000000; x++) {;}
console.log(number);
}), 3000);
console.log("done");
var async_func=函数(x,func){
func(x+5);
};
setTimeout(异步函数(5,函数(编号){
对于(var x=0;x<100000000;x++){;}
控制台日志(编号);
}), 3000);
控制台日志(“完成”);
试试:
(我还删除了(var x=0;x<100000000;x++){;}的不必要的)
在调用setTimeout中带有参数的函数时,如果不使用匿名函数或帮助函数。。。(如果您真的想在不设置其他功能的情况下执行此操作,请检查@Ian comments bellow。)
如果您的函数没有任何参数,则可以执行setTimeout(async_func,3000)代码>但在这种情况下,最好是通过匿名函数调用它(或在使用这些参数调用函数之前声明调用函数)。尝试:
function async_func(x, func) {
func(x+5);
}
function timer_func() {
async_func(5, function(number) {
for (var x = 0; x < 1000000000; x++) {;}
console.log(number);
});
}
setTimeout(timer_func, 3000);
console.log("done");
(我还删除了(var x=0;x<100000000;x++){;}
的不必要的)
在调用setTimeout中带有参数的函数时,如果不使用匿名函数或帮助函数…(如果您确实想在不设置另一个函数check@Ian comments bellow的情况下执行此操作)。
如果您的函数没有任何参数,您可以执行setTimeout(async_func,3000);
但是在这种情况下,最好是通过匿名函数调用它(或者在使用这些参数调用函数的上面声明调用函数)。这是使用setTimeout()时的常见错误
以及在传递函数引用时,要在其中调用带参数的函数。这行代码:
setTimeout( async_func(5, function(number) {
function async_func(x, func) {
func(x+5);
}
function timer_func() {
async_func(5, function(number) {
for (var x = 0; x < 1000000000; x++) {;}
console.log(number);
});
}
setTimeout(timer_func, 3000);
console.log("done");
立即执行async_func()
,然后将其返回结果(不是函数)传递给setTimeout()
,这不是您想要的。您希望传递对setTimeout()
的函数引用,以便setTimeout()
以后可以这样调用该函数:
var async_func = function(x, func) {
func(x+5);
};
setTimeout( function() {
async_func(5, function(number) {
for (var x = 0; x < 1000000000; x++) {;}
console.log(number);
});
}, 3000);
console.log("done");
var async_func=函数(x,func){
func(x+5);
};
setTimeout(函数(){
异步函数(5,函数(数字){
对于(var x=0;x<100000000;x++){;}
控制台日志(编号);
});
}, 3000);
控制台日志(“完成”);
或者,有时更容易理解的方法是将计时器回调函数设置为自己的独立函数,不带任何参数
function async_func(x, func) {
func(x+5);
}
function timer_func() {
async_func(5, function(number) {
for (var x = 0; x < 1000000000; x++) {;}
console.log(number);
});
}
setTimeout(timer_func, 3000);
console.log("done");
函数异步函数(x,func){
func(x+5);
}
函数计时器_func(){
异步函数(5,函数(数字){
对于(var x=0;x<100000000;x++){;}
控制台日志(编号);
});
}
设置超时(定时器功能,3000);
控制台日志(“完成”);
使用setTimeout()
和传递函数引用时,如果要调用带参数的函数,这是一个常见错误。这行代码:
setTimeout( async_func(5, function(number) {
立即执行async_func()
,然后将其返回结果(不是函数)传递给setTimeout()
,这不是您想要的。您希望传递对setTimeout()
的函数引用,以便setTimeout()
以后可以这样调用该函数:
var async_func = function(x, func) {
func(x+5);
};
setTimeout( function() {
async_func(5, function(number) {
for (var x = 0; x < 1000000000; x++) {;}
console.log(number);
});
}, 3000);
console.log("done");
var async_func=函数(x,func){
func(x+5);
};
setTimeout(函数(){
异步函数(5,函数(数字){
对于(var x=0;x<100000000;x++){;}
控制台日志(编号);
});
}, 3000);
控制台日志(“完成”);
或者,有时更容易理解的方法是将计时器回调函数设置为自己的独立函数,不带任何参数
function async_func(x, func) {
func(x+5);
}
function timer_func() {
async_func(5, function(number) {
for (var x = 0; x < 1000000000; x++) {;}
console.log(number);
});
}
setTimeout(timer_func, 3000);
console.log("done");
函数异步函数(x,func){
func(x+5);
}
函数计时器_func(){
异步函数(5,函数(数字){
对于(var x=0;x<100000000;x++){;}
控制台日志(编号);
});
}
设置超时(定时器功能,3000);
控制台日志(“完成”);
非常清楚的解释!但是为什么单独运行我的async_func而没有计时器仍然会阻塞?我试图在internet上查找信息,但似乎找不到我要查找的确切内容“阻塞”是什么意思?async_func
本身并不是一个异步函数,所以它当然应该是阻塞的。解释得很清楚!但是为什么单独运行我的async_func,没有计时器仍然阻塞?我试图在internet上查找信息,但似乎找不到我要查找的确切内容“阻塞”是什么意思?async_func
本身并不是一个异步函数,所以它当然应该被阻止。非常感谢,但是为什么setTimeout不能处理带参数的函数?如果不生成匿名函数,就不能在setTimeout中调用带参数的函数……好吧,从技术上讲,可以-可以使用setTimeout
的第一个参数一个字符串,所以你可以用串接字符串和变量来构造函数调用,比如:setTimeout(“myFunction(“+var1+””),200);
但这在可能的任何情况下都不是理想的:)@Ian这是一个解决方案,但不是最好的方法。@JuanCruzViotti,只需删除带有for(var x=0;x<100000000;x++)的行即可{;}
而且它会毫无问题地工作。(我已经更新了我的答案)@Whiteagle哈哈,我知道这不是最好的方法……我不确定我是否会建议这样做。虽然我确定有时间和地点,但它会对某些事情有好处。我只是想指出,在setTimeout中调用带有参数的函数而没有匿名函数的说法并不完全正确。@Ian你是对的,我在wri时错了用“不能”代替“应该”:更新了我的答案。非常感谢,但是为什么setTimeout不能处理带参数的函数呢?如果不生成匿名函数,就无法在setTimeout中调用带参数的函数……好吧,从技术上讲,您可以–setTimeout的第一个参数可以是字符串,因此您可以使用concaten构造函数调用