Node.js:异步回调执行.这是Zalgo吗? [英] Node.js: Asynchronous Callback Execution. Is this Zalgo?

查看:239
本文介绍了Node.js:异步回调执行.这是Zalgo吗?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

使用节点-6.0执行以下操作.

function A(callback) {
  console.log('A');
  callback();
}

function B() {
  console.log('B')
}

function C() {
  console.log('C');
}

A(C);
B();


// Result is A,C,B i expected that A, B, C

但是将上面的示例更改为使用process.nextTick()打印A,B,C

But changing the above example to use process.nextTick() prints A, B, C

function A(callback) {
  console.log('A');
  process.nextTick(() => {
    callback();
  });
}

function B() {
  console.log('B')
}

function C() {
  console.log('C');
}

A(C);
B();

这就是我们所说的zalgo吗?谁能提供给我一个实时的例子,这会导致重大故障?

Is this what we call as zalgo ? Can anyone provide me a realtime example of this, which will cause major breakdown ?

推荐答案

首先让我解释一下代码的工作原理-查看我添加的代码中的注释:

First let me explain how the code works - see the comments in the code that I added:

// first you define function A and nothing happens:
function A(callback) {
  console.log('A');
  callback();
}

// then you define function B and nothing happens:    
function B() {
  console.log('B')
}

// then you define function C and nothing happens:
function C() {
  console.log('C');
}

// now you call function A with argument C:
A(C);
// when A runs it prints 'A' and calls C before it returns
// now the C runs, prints C and returns - back to A
// A now has nothing more to do and returns

// Now the execution continues and B can be run:
B();
// B runs and prints 'B'

这与Java,C等任何语言中的完全相同.

This is exactly the same as it would be in any language like Java, C etc.

现在,第二个示例:

// first you define function A and nothing happens:
function A(callback) {
  console.log('A');
  process.nextTick(() => {
    callback();
  });
}

// then you define function B and nothing happens:
function B() {
  console.log('B')
}

// then you define function C and nothing happens:
function C() {
  console.log('C');
}

// Then you run A with C passed as an argument:
A(C);
// A prints 'A' and schedules running an anonymous function:
// () => { callback(); }
// on the next tick of the event loop, before I/O events are handled
// but after the current code stack is unrolled
// then it returns
// And then B is run:
B();
// B prints 'B' and returns
// Now nothing else is left to do so the next tick of the event loop starts
// There's one function to run, scheduled earlier so it runs.
// This function runs the `callback()` which was `C`
// so C starts, prints 'C' and returns
// The anonymous function has nothing else to do and returns
// There is no more things on the event loop so the program exits

更新

感谢Bergi解释了Zalgo在他的回答中是什么.现在,我更好地了解了您的担忧.

Update

Thanks to Bergi for explaining what is Zalgo in his answer. Now I better understand your concerns.

这就是我们所说的zalgo吗?谁能提供给我一个实时的例子,这会导致重大故障?

Is this what we call as zalgo ? Can anyone provide me a realtime example of this, which will cause major breakdown ?

我看过很多这样的代码:

I've seen a lot of code like this:

function x(argument, callback) {
    if (!argument) {
        return callback(new Error('Bad argument'));
    }
    runSomeAsyncFunction(argument, (error, result) => {
        if (error) {
            return callback(new Error('Error in async function'));
        }
        callback({data: result});
    });
}

现在,如果存在错误的参数,则可以在x()返回之前立即运行回调,否则可以在x()返回之后运行回调.这段代码很普通.为了测试这些论点,人们可能会争辩说应该抛出一个异常,但是让我们暂时忽略一下,可能会有一些更好的操作错误示例立即被知道-这只是一个简单的示例.

Now, the callback can be either run immediately before x() returns if there are bad arguments, or after the x() returns otherwise. This code is very common. For testing the arguments one could argue that it should throw an exception but let's ignore that for a moment, there may be some better examples of operational errors that are known immediately - this is just a simple example.

现在,如果它是这样写的:

Now, if it was written like this:

function x(argument, callback) {
    if (!argument) {
        return process.nextTick(callback, new Error('Bad argument'));
    }
    runSomeAsyncFunction(argument, (error, result) => {
        if (error) {
            return callback(new Error('Error in async function'));
        }
        callback({data: result});
    });
}

可以保证在x()返回之前永远不会调用该回调.

it would be guaranteed that the callback will never be invoked before x() returns.

现在,是否可能导致重大故障"完全取决于其使用方式.如果您运行类似这样的内容:

Now, if that can cause a "major breakdown" depends entirely on how it is used. If you run something like this:

let a;
x('arg', (err, result) => {
    // assume that 'a' has a value
    console.log(a.value);
});
// assign a value to 'a' here:
a = {value: 10};

然后,有时在没有process.nextTick的情况下,它会在x()版本的情况下崩溃,并且在process.nextTick()的情况下,它永远不会与x()的版本崩溃.

then it will sometimes crash with the version of x() without process.nextTick and will never crash with the version of x() with process.nextTick().

这篇关于Node.js:异步回调执行.这是Zalgo吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆