1.同步API,异步API的区别(获取返回值)
同步API可以从返回值中拿到API执行的结果,但是异步API是不可以的。
1 // 同步 2 function sum (n1, n2) { 3 return n1 + n2; 4 } 5 const result = sum (10, 20);
1 // 异步 2 function getMsg() { 3 setTimeout(function() { 4 return {msg: 'hello node.js'} 5 }, 2000); 6 } 7 const msg = getMsg(); 8 console.log(msg); // undefined
2. 回调函数
自己定义函数让别人去调用。
// getData函数定义 function getData (callback) {} // getData函数调用 getData (() => {});
3. 代码执行顺序分析
console.log('代码开始执行'); setTimeout(() => { console.log('2秒后执行的代码'); }, 2000); setTimeout(() => { console.log('"0秒"后执行的代码'); }, 0); console.log('代码结束执行');
4. promise
promise出现的目的是解决node.js异步编程中回调地狱的问题。
let promise = new Promise((resolve, reject) => { setTimeout(()=> { if (true) { resolve({name: '张三'}) } else { reject('失败了') } }, 2000); }); promise.then(result => console.log(result)) // {name: '张三'} .catch(error => console.log(error)); // 失败了
const fs = require('fs'); let promise = new Promise((resolve, reject)=> { fs.readFile('./1.txt', 'utf8', (err, result)=> { if( err !== null) { reject(err) } else { resolve(result); } }) }); promise.then((result)=> { console.log(result); })
先后打印三个异步函数
1 const fs = require('fs'); 2 function p1() { 3 return new Promise((resolve, reject)=> { 4 fs.readFile('./1.txt', 'utf8', (err, result)=> { 5 if( err !== null) { 6 reject(err) 7 } else { 8 resolve(result); 9 } 10 11 }) 12 }); 13 } 14 function p2() { 15 return new Promise((resolve, reject)=> { 16 fs.readFile('./2.txt', 'utf8', (err, result)=> { 17 if( err !== null) { 18 reject(err) 19 } else { 20 resolve(result); 21 } 22 }) 23 }); 24 } 25 function p3() { 26 return new Promise((resolve, reject)=> { 27 fs.readFile('./3.txt', 'utf8', (err, result)=> { 28 if( err !== null) { 29 reject(err) 30 } else { 31 resolve(result); 32 } 33 }) 34 }); 35 } 36 37 p1().then(r1 => { 38 console.log(r1); 39 return p2(); 40 }).then(r2 => { 41 console.log(r2); 42 return p3(); 43 }).then(r3 => { 44 console.log(r3); 45 })
5. async
异步函数是异步编程语法的终极解决方案,它可以让我们将异步代码变成同步的形式,让代码不再有回调函数嵌套,使代码变得清晰明了。
- 在普通函数定义的前面加上async关键字,普通函数就变成了异步函数
- 异步函数默认的返回值是promise对象
- 在异步函数内使用throw关键字进行错误的抛出
1 // 1. 在普通函数定义的前面加上async关键字,普通函数就变成了异步函数 2 // 2. 异步函数默认的返回值是promise对象 3 // 3. 在异步函数内使用throw关键字进行错误的抛出 4 async function fn () { 5 throw '发生了一些错误' 6 return 123; 7 } 8 fn().then(data => { 9 console.log(data) 10 }).catch(error=> { 11 console.log(error); 12 })
await关键字
- 它只能出现在异步函数中
- await promise 它可以暂停异步函数的执行,等待promise对象返回结果后再向下执行函数
1 async function p1() { 2 return 'p1'; 3 } 4 async function p2() { 5 return 'p2'; 6 } 7 async function p3() { 8 return 'p3'; 9 } 10 async function run () { 11 await p1() 12 await p2() 13 await p3() 14 }
1 const fs = require('fs'); 2 const promisify = require('util').promisify; 3 4 const readFile = promisify(fs.readFile); 5 6 async function run () { 7 let r1 = await readFile('./1.txt', 'utf8'); 8 let r2 = await readFile('./2.txt', 'utf8'); 9 let r3 = await readFile('./3.txt', 'utf8'); 10 console.log(r1); 11 console.log(r2); 12 console.log(r3); 13 } 14 run();