The generator

Define the form

The function is defined to increment *(asterisk) immediately after function, and uses yield inside the function, which returns one value at a time

Iterators: Generator functions are very different from normal functions in that they are called directly to form iterators

function* conso()
		{
			yield 1
			yield 2
			yield 3
			yield 4
			yield 5
		}
Copy the code

How do you get the value of the generator since it’s not like a normal function? The for-of loop is now iterator!! Because it’s called directly!

For (let val of conso()) {console.log(val)} // The result prints /* 1 2 3 4 5 */Copy the code

Generators can now fetch values. What about iterators? We can use the while iterator to return that the object contains two values. {value, done} ‘ ‘is true if iteration is not possible, so we can loop with the done value

var diedaiqi = conso() var diedaiqi = conso() while(! ((item = diedaiqi.next()).done)) { console.log(item.value, item) } /* 1 {value: 1, done: false} 2 {value: 2, done: false} 3 {value: 3, done: false} 4 {value: 4, done: false} 5 {value: 5, done: false} */Copy the code

Transfer generator

See what print down here?

Used on iteratorsyield*Operator to jump to another generator for execution.

Function * firstGenerator() {yield 'first-name' yield* secondGenerator() Yield 'first-age'} function* secondGenerator() {yield 'second-name' yield 'second-age'} for (let gVal of  firstGenerator()) { console.log(gVal) } /* first-name second-name second-age first-age */Copy the code

And what is it now?

function* testGenerator()
{
	let i = 0;
	while(true) {
	  yield ++i
	    }
	}

console.log(testGenerator().next().value) // 1
console.log(testGenerator().next().value) // 1
console.log(testGenerator().next().value) // 1
Copy the code

It’s the same as your guess. It’s all 1’s. Therefore, if you get a unique ID this way, you assign the iterator to a variable and use it.

function* testGenerator()
		{
			let i = 0;
			while(true) {
				yield ++i
			}
		}

		let testIterator = testGenerator()
		console.log(testIterator.next().value) // 1
		console.log(testIterator.next().value) // 2
		console.log(testIterator.next().value) // 3
Copy the code

Generator parameter

Like normal functions, functions define parameters and pass arguments when called

function* NinjaGenerator(action) {
			const imposter = yield ("Hattori " + action); 
			console.log(imposter)

			const zhy = yield ("Yoshi (" + imposter + ") " + action); 

			yield ("Yoshi (" + zhy + ") " + action); 
		}

		const ninjaIterator = NinjaGenerator("skulk");
		const result1 = ninjaIterator.next();
		console.log(result1) // {value: "Hattori skulk", done: false}
		const result2 = ninjaIterator.next("Hanzo");
		console.log(result2) // {value: "Yoshi (Hanzo) skulk", done: false}
		const result3 = ninjaIterator.next("wobuzhidao");
		console.log(result3) // {value: "Yoshi (wobuzhidao) skulk", done: false}
Copy the code

Explanation: In this example we called the next method of ninjaIterator twice. The first call to ninjaiterator.next () requests the first value of the generator. Since the generator has not yet started executing, this call starts the generator, evaluates the expression “Hattori “+ Action to get the value “Hattori skulk” and suspends execution of the generator. There’s nothing special about this. We’ve done this many times. However, something interesting happened to the next method called ninjaIterator the second time: Ninjaiterator.next (“Hanzo”). This time, we use the next method to pass the calculated value back to the generator. The generator function waits patiently, at the expression yield (“Hattori”

  • The action position hangs, so the value Hanzo is passed as an argument to the next() method and used as an integer

The value of the yield expression. In this case, the statement imattori = yield (“Hattori”

  • The final value of the variable imposter in action is Hanzo.

This shows how to communicate both ways in a generator. We return the value from the generator using the yield statement and use the iterator’s next() method to pass the value back to the generator. Javascript Ninja Secrets -P185

When next() is passed in, it replaces the entire yield value, but it didn’t work the first time. In the book, it says the generator works the second time. And so on…

When a generator contains a return statement, subsequent statements are not executed

function* testD() { return 123; yield 1111; yield 2222; } var tt = testD() while(! ((item = tt.next()).done)) {console.log(item.value, item)} // 1111 and 2222 will not be printedCopy the code

What does this print?

const promise = new Promise((resolve, reject) => {
resolve("Hattori");
setTimeout(()=> reject("Yoshi"), 500);
});
promise.then(val => alert("Success: " + val))
.catch(e => alert("Error: " + e));
Copy the code

The result is: Success: Hattori ⚠️ : After walking into the Success function, even if the failure callback is called, it is not executed? Why is that?

Question 2

const promise1 = new Promise((resolve, reject) => { resolve('123') reject('0000') }) promise1.then(data => console.log(data)).catch(err => console.log(err)) // Results: 123Copy the code

Question 3

const promise1 = new Promise((resolve, reject) => { reject('0000') resolve('123') }) promise1.then(data => console.log(data)).catch(err => console.log(err)) // Results: 0000Copy the code

Conclusion: If both the success and failure functions of a Promise are executed, the latter function will not be executed.

Promise

To solve asynchronous callback hell, Promise’s previous callbacks must all get results before they can be executed!

var ninjas, mapInfo, plan; $.get("data/ninjas.json", function(err, data) { if(err) { processError(err); return; } ninjas = data; actionItemArrived(); }); $.get("data/mapInfo.json", function(err, data) { if(err) { processError(err); return; } mapInfo = data; actionItemArrived(); }); $.get("plan.json", function(err, data) { if(err) { processError(err); return; } plan = data; actionItemArrived (); }); function actionItemArrived() { if(ninjas ! = null && mapInfo ! = null && plan ! = null){ console.log("The plan is ready to be set in motion!" ); } } function processError(err) { alert("Error", err) }Copy the code

Refused to Promise

Explicit rejection, which calls the incoming reject method in a promise’s execution function; Implicit rejection, an exception thrown in the process of processing a promise.

An instance of a Promise request

function getJson(url) { return new Promise((resolve, reject) => { let xhr = new XMLHttpRequest() xhr.open('GET', url) xhr.onload = () => { try { if (xhr.status == 200) { resolve(JSON.parse(xhr.response)) } else { reject(xhr.status + ' failed! ') } } catch(e) { reject(e.getMessage()) } } xhr.onerror = () => { reject(xhr.status + ' failed! onerror') } xhr.send() }) } getJson('http://php.test.com:8081/zhy/index.php'). then(data => console.log(data)). then(() => getJson('http://php.test.com:8081/zhy/a.php')). then(datas => console.log(datas)). then(() => GetJson (' http://php.test.com:8081/zhy/b.php ')). Then (datab = > console. The log (datab)). The catch (err = > console. The log (err)) / / results {name: "a.php ", age: 23} {name: "a.php ", age: 33} {name: "a.php ", age: 44}Copy the code

Promise. All applications

In parallel requests, all of the results are valid so you go to the THEN success function, otherwise you catch the exception and you catch the first exception that you get

Promise.all([getJson('http://php.test.com:8081/zhy/index.php'), getJson('http://php.test.com:8081/zhy/a.php'), getJson('http://php.test.com:8081/zhy/b.php')]). then(results => console.log(results)). catch(err => console.log(err)) // result [{name: "a.php ", age: 23} {name: "a.php ", age: 33} {name: "a.php ", age: 44}]Copy the code

Promise.race

It is also a parallel request, but only the first result is taken, and subsequent results are discarded, as is the case with catching exceptions

Promise.race([getJson('http://php.test.com:8081/zhy/index.php'), getJson('http://php.test.com:8081/zhy/a.php'), getJson('http://php.test.com:8081/zhy/b.php')]). then(results => console.log(results)). catch(err => Console. log(22222222, err)) // The result may not be one of the three (open question 😄)Copy the code

Promise has more knowledge, here is not a careful explanation, just say common usage, to help beginners quickly start!!

Generators are used in combination with promises

I don’t really understand. The feeling is to take advantage of the generator’s ability to call back when a Promise is executed

Future function async

async.. Await is the syntactic sugar of Promise and generator. The advantage is that we can use the result of the first request on the second request!

(async function() { const data = await getJson('http://php.test.com:8081/zhy/index.php'); console.log(data) const data1 = await getJson('http://php.test.com:8081/zhy/a.php'); Console. log(data1)})() {name: "contents of index.php ", age: 23} {name:" contents of index.php ", age: 33}Copy the code