Node.js 中的异步模式
由于节点是一种在单个线程上运行的语言,而该线程又在后台使用多个线程。 node.js 中的代码应该是非阻塞的,因为如果特定的代码行,例如:读取一个大文档可能会停止执行它前面的所有代码行,这不是一个好习惯。
这就是为什么要实现可能需要一些时间的功能,它是以异步方式完成的,这使得该特定部分的执行脱离了主事件循环并且程序正常运行。
异步的三种模式:
- 回调
- 承诺
- 异步等待
1.回调:回调函数是作为函数传递给另一个函数的函数,然后在外部函数内部调用该函数以完成某种例程或动作。
该函数在异步操作完成时调用。主要是回调函数体包含异步操作。
最常见的形式是“错误优先”回调,其中如果父函数并接受错误参数,如果有错误则执行错误部分,否则执行另一部分。
文件名:index.js
javascript
arr = ["Geeks", "Geeks", "pop", "Geeks"]
console.log("calling")
var value = arr.filter(function(element) {
if(element != "pop")
return element
});
console.log("called")
console.log(value)
javascript
const multiplication = (numberOne, numberTwo) => {
return new Promise((resolve, reject) => {
setTimeout(() => {
// Checking if any number is negative or not
if (numberOne < 0 || numberTwo < 0) {
// If everything is not fine
return reject("Only Positive number allowed")
}
// If everything is fine
resolve(numberOne * numberTwo)
}, 1000)
})
}
// Call for positive numbers
multiplication(5, 3).then((product) => {
console.log("The product is:", product)
}).catch((error) => {
console.log(error)
})
// Call for negative numbers
multiplication(5, -3).then((product) => {
console.log("The product is:", product)
}).catch((error) => {
console.log(error)
})
javascript
function resolvelater() {
return new Promise(resolve => {
setTimeout(() => {
resolve('GeeksforGeeks');
}, 2000);
});
}
async function waitforGeeksforGeeks() {
console.log('calling');
const result = await resolvelater();
console.log(result);
}
waitforGeeksforGeeks()
使用以下命令运行index.js文件:
node index.js
输出:
calling
called
[ 'Geeks', 'Geeks', 'Geeks' ]
通常不使用回调,因为异步操作之后的所有代码都嵌套在一个函数中。更多的异步操作意味着更多的缩进,最终导致不可读和混乱,并且随着更大的功能问题变得越来越重要。它也被称为“死亡金字塔”。
2. Promises: Promise 是状态或值的代理,在创建 Promise 的那一刻是未知的,但可以在不久的将来确定。这让异步方法可以返回一个承诺,在未来的某个时候提供价值。
基本语法:
const promise = new Promise(function)
他们有以下方法:
- 原型.then()
- 原型.catch()
.then() 用于指定如果promise 被履行时要做什么,.catch() 用来指定promise 没有履行时要做什么。
文件名:index.js
javascript
const multiplication = (numberOne, numberTwo) => {
return new Promise((resolve, reject) => {
setTimeout(() => {
// Checking if any number is negative or not
if (numberOne < 0 || numberTwo < 0) {
// If everything is not fine
return reject("Only Positive number allowed")
}
// If everything is fine
resolve(numberOne * numberTwo)
}, 1000)
})
}
// Call for positive numbers
multiplication(5, 3).then((product) => {
console.log("The product is:", product)
}).catch((error) => {
console.log(error)
})
// Call for negative numbers
multiplication(5, -3).then((product) => {
console.log("The product is:", product)
}).catch((error) => {
console.log(error)
})
使用以下命令运行index.js文件:
node index.js
输出:
The product is: 15
Only Positive number allowed
3. async-await:父函数声明为async关键字,内部允许使用await关键字的方法。 async 和 await 关键字启用异步的、基于 Promise 的行为,这样代码可以写得更干净,避免 Promise 链。
基本语法:
async function name(params) {
const result = await waitforfunction()
}
异步函数可以包含多个等待表达式。这个 await 关键字用于等待承诺被履行或被拒绝。
文件名:index.js
javascript
function resolvelater() {
return new Promise(resolve => {
setTimeout(() => {
resolve('GeeksforGeeks');
}, 2000);
});
}
async function waitforGeeksforGeeks() {
console.log('calling');
const result = await resolvelater();
console.log(result);
}
waitforGeeksforGeeks()
使用以下命令运行index.js文件:
node index.js
输出:
calling
GeeksforGeeks