Promise is pretty familiar, considering just a few apis, but do you really know Promise? See how many of the 10 questions you can answer correctly, based on some Promise points.
The following promises refer to promise instances in node.js.
Subject to a
const promise = new Promise((resolve, reject) => {
console.log(1)
resolve()
console.log(2)
})
promise.then(() => {
console.log(3)
})
console.log(4)Copy the code
Running results:
1 2 3 4Copy the code
Explanation: The Promise constructor is executed synchronously, while the functions in promise.then are executed asynchronously.
Topic 2
const promise1 = new Promise((resolve, reject) => { setTimeout(() => { resolve('success') }, 1000) }) const promise2 = promise1.then(() => { throw new Error('error!!! ') }) console.log('promise1', promise1) console.log('promise2', promise2) setTimeout(() => { console.log('promise1', promise1) console.log('promise2', promise2) }, 2000)Copy the code
Running results:
promise1 Promise { <pending> } promise2 Promise { <pending> } (node:50928) UnhandledPromiseRejectionWarning: Unhandled promise rejection (rejection id: 1): Error: error!!! (node:50928) [DEP0018] DeprecationWarning: Unhandled promise rejections are deprecated. In the future, promise rejections that are not handled will terminate the Node.js process with a non-zero exit code. promise1 Promise { 'success' } promise2 Promise { <rejected> Error: error!!! at promise.then (...) at <anonymous> }Copy the code
A promise has three states: Pending, depressing or Rejected. The state change can only be pending-> depressing or pending-> Rejected. Once the state changes, it cannot be changed again. Promise2 above is not promisE1, but a new Promise instance returned.
The title three
const promise = new Promise((resolve, reject) => {
resolve('success1')
reject('error')
resolve('success2')
})
promise
.then((res) => {
console.log('then: ', res)
})
.catch((err) => {
console.log('catch: ', err)
})Copy the code
Running results:
then: success1Copy the code
The resolve or reject constructor is valid only on the first execution, and multiple calls have no effect, echoing code 2’s conclusion that once a promise state changes, it cannot be changed again.
The title four
Promise.resolve(1)
.then((res) => {
console.log(res)
return 2
})
.catch((err) => {
return 3
})
.then((res) => {
console.log(res)
})Copy the code
Running results:
1
2Copy the code
Explanation: Promises can be called chained. When we think of chained calls we usually think of a return this implementation, but that’s not how promises are implemented. A promise returns a new promise each time it is called. Then or. Catch, thereby implementing the chained invocation.
Topic five
const promise = new Promise((resolve, reject) => {
setTimeout(() => {
console.log('once')
resolve('success')
}, 1000)
})
const start = Date.now()
promise.then((res) => {
console.log(res, Date.now() - start)
})
promise.then((res) => {
console.log(res, Date.now() - start)
})Copy the code
Running results:
once
success 1005
success 1007Copy the code
Explanation: A promise’s.then or.catch can be called multiple times, but here the Promise constructor is executed only once. Or once the internal state of a promise changes and it has a value, each subsequent call to.then or.catch will get that value directly.
Topic 6
Promise.resolve() .then(() => { return new Error('error!!! ') }) .then((res) => { console.log('then: ', res) }) .catch((err) => { console.log('catch: ', err) })Copy the code
Running results:
then: Error: error!!!
at Promise.resolve.then (...)
at ...Copy the code
An error object in a. Then or. Catch does not throw an error, so it will not be caught by a subsequent. Catch.
return Promise.reject(new Error('error!!! ')) throw new Error('error!!! ')Copy the code
Return new Error(‘ Error!!! ‘) because returning any non-Promise value is wrapped as a Promise object. ‘) equivalent to return promise.resolve (new Error(‘ Error!!! ‘)).
Title seven
const promise = Promise.resolve()
.then(() => {
return promise
})
promise.catch(console.error)Copy the code
Running results:
TypeError: Chaining cycle detected for promise #<Promise>
at <anonymous>
at process._tickCallback (internal/process/next_tick.js:188:7)
at Function.Module.runMain (module.js:667:11)
at startup (bootstrap_node.js:187:16)
at bootstrap_node.js:607:3Copy the code
Explanation: The value returned by. Then or. Catch cannot be the promise itself, otherwise an infinite loop will occur. Similar to:
process.nextTick(function tick () {
console.log('tick')
process.nextTick(tick)
})Copy the code
The title eight
Promise.resolve(1)
.then(2)
.then(Promise.resolve(3))
.then(console.log)Copy the code
Running results:
1Copy the code
Explanation:.then or.catch parameters are expected to be functions, and passing non-functions will result in value penetration.
Title nine
Promise.resolve()
.then(function success (res) {
throw new Error('error')
}, function fail1 (e) {
console.error('fail1: ', e)
})
.catch(function fail2 (e) {
console.error('fail2: ', e)
})Copy the code
Running results:
fail2: Error: error
at success (...)
at ...Copy the code
Explanation:.then can take two arguments, the first being the function that handled success and the second being the function that handled error. .catch is a shorthand for the second argument to.then, but they are used with a caveat: the second error-handling function of.then does not catch the error thrown by the first successful function, while subsequent.catches catch the previous error. Of course the following code can also be used:
Promise.resolve()
.then(function success1 (res) {
throw new Error('error')
}, function fail1 (e) {
console.error('fail1: ', e)
})
.then(function success2 (res) {
}, function fail2 (e) {
console.error('fail2: ', e)
})Copy the code
The title ten
process.nextTick(() => {
console.log('nextTick')
})
Promise.resolve()
.then(() => {
console.log('then')
})
setImmediate(() => {
console.log('setImmediate')
})
console.log('end')Copy the code
Running results:
end
nextTick
then
setImmediateCopy the code
Both Process.nexttick and Promise.then are microtasks, while setImmediate is macroTask and is performed during the check phase of the event loop. Microtasks are executed between each phase of the event cycle (MacroTasks), with a MicroTask executed at the beginning of the event cycle.
This article is written by NSWBMW of graphite documents.