首頁 >web前端 >js教程 >深入淺析Node.js非同步程式設計中的callback(回呼)

深入淺析Node.js非同步程式設計中的callback(回呼)

青灯夜游
青灯夜游轉載
2021-07-06 11:30:182708瀏覽

非阻塞 I/O 的運行結果是需要回呼函數來接收的,以下這篇文章給大家詳細介紹一下Node.js非同步程式設計中的callback(回呼)。

深入淺析Node.js非同步程式設計中的callback(回呼)

【推薦學習:《nodejs 教學》】

非阻塞I/O 的運作結果是需要回呼函數來接收的,這種透過回呼函數的方式就是非同步程式設計!

非同步程式設計案例一##
function interview(callback) {
  setTimeout(() => {
    callback("success");
  }, 1000);
}

interview(function (res) {
  if (res === "success") {
    console.log("============我笑了");
  }
});

回呼函數格式規格

    error-first callbak
  • Node-style callback
  • 第一個參數是error,後面的參數才是結果

為什麼第一個參數是error
function interview(callback) {
  setTimeout(() => {
    if (Math.random() < 0.3) {
      callback("success");
    }
    throw new Error("fail");
  }, 1000);
}

try {
  interview(function (res) {
    if (res === "success") {
      console.log("============我笑了");
    }
  });
} catch (error) {
  console.log("fail", error);
}

深入淺析Node.js非同步程式設計中的callback(回呼)

上面的程式碼中,

try catch並不能捕獲 throw new Error('fail') 拋出的錯誤! ,而是拋出到了 JS 全域!在 Node.js 中,全域錯誤時非常嚴重的事情,會造成程式的崩潰!

為什麼沒

try catch 無法捕捉 setTimeout 裡面的 throw 呢?這就跟呼叫堆疊事件循環有關係了!

每一個事件循環都是一個全新的呼叫堆疊! setTimeout 與interview 是兩個不同的事件循環!

但是可以透過在回呼函數中的參數拋出錯誤的方式來解決這個問題

function interview(callback) {
  setTimeout(() => {
    if (Math.random() < 0.3) {
      callback(null, "success");
    } else {
      callback(new Error("fail"));
    }
  }, 1000);
}

interview(function (error) {
  if (error) {
    return console.log("============我哭了");
  }
  console.log("============我笑了");
});

上面的程式碼中,可以根據參數的類型來判斷是否出錯!但是 Node.js 中有很對回呼函數, 我們不可能在每個函數中都去判斷參數型別是是否出錯!

Node.js 規定第一個參數就是 erro,第二個參數就是結果!如果第一個參數不為空,則表示非同步呼叫出錯了!

非同步流程控制的問題

回呼地獄

多個非同步任務序列的情況, 下面我們模擬一下N 輪面試,

function interview(callback) {
  setTimeout(() => {
    if (Math.random() < 0.6) {
      callback(null, "success");
    } else {
      callback(new Error("fail"));
    }
  }, 1000);
}

interview(function (error) {
  if (error) {
    return console.log("======第一轮面试======我哭了");
  }

  interview(function (error) {
    if (error) {
      return console.log("====第二轮面试========我哭了");
    }

    interview(function (error) {
      if (error) {
        return console.log("====第三轮面试========我哭了");
      }

      console.log("三轮面试都成功了!啊哈哈哈!");
    });
  });
});

可以看到上面的非同步流程做了三層嵌套,這還只是程式碼就比較簡單的情況!那麼在實際應用中,每一個巢狀函數都可能非常複雜,這就造成難以開發和維護,看著讓人生氣,這就是所謂的** 回調地獄**

a

多個非同步任務並發的情況

function interviewCompay() {
  let count = 0;
  interview(function (error) {
    if (error) {
      return console.log("====第一家公司面试========我哭了");
    }
    count++;
  });
  interview(function (error) {
    if (error) {
      return console.log("====第二家公司面试========我哭了");
    }
    count++;
    if (count === 2) {
      return console.log("两家公司面试都成功了!我笑了");
    }
  });
}
interviewCompay();

在每個非同步任務裡面都需要加入同一個變數才能捕捉多個非同步任務的結果

解決非同步流程的控制問題

    promise
  • async await
更多程式相關知識,請造訪:

程式影片! !

以上是深入淺析Node.js非同步程式設計中的callback(回呼)的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文轉載於:juejin.cn。如有侵權,請聯絡admin@php.cn刪除