JS|コールバック関数が返されます🪃
20958 ワード
JavaScriptの開発者であれば、呼吸のようにコールバック関数を使用できます.しかし、本当にコールバック関数が何なのかと聞くと、簡単には答えられない.コールバック関数はAPI通信などの非同期論理を記述する際に必要であるため,これらの概念を理解してこそコードを正確に記述することができる.
コールバック関数
匿名コールバック関数をすべて「記名関数」に変更する方法 . Promise(ES6) Generator(ES6) async/await(ES2017)
コールバック関数
コールバック(callback)は「コールバック」を表します.
すなわち、関数Aが呼び出されると、ある条件が満たされると、関数Bが実行され、自身に通知する要求が発行される.
要求を受けた関数Aは、これらの条件が満たされているか否かを自ら判断し、関数Bを直接呼び出す.
コールバック関数は、別のコードのパラメータとして渡され、「制御権」が同時に委任された関数を指します.
コールバック関数を受信したコードは、内部論理に基づいて適切な時間にコールバック関数を実行します.
💡 パラメータを介して関数の外部からコールバック関数を渡す関数を「高次関数」と呼びます.高次関数にコールバック関数を渡す場合は、関数自体を渡す必要があります.
コールバック関数は,関数式プログラミングモードだけでなく,イベント処理,Ajax通信などの非同期処理の一般的なモードである.
コールバック関数の制御
コールポイント
コールバック関数を渡すコードには、コールバック関数呼び出しポイントの制御権があります.var count = 0;
var timer = setInterval(function() { // setInterval 함수가 콜백 함수의 제어권을 넘겨받음.
console.log(count);
if(++count > 4) clearInterval(timer);
}, 1000);
// 1초 후
// 0
// 1초 후
// 1
// 1초 후
// 2
// 1초 후
// 3
// 1초 후
// 4
けいすう
コールバック関数の制御権を受け入れるコードは、コールバック関数を呼び出すときに、パラメータにどの値をどの順序で渡すかを制御します.
コールバック関数を呼び出すと、パラメータに渡される値とその順序が決定されるので、パラメータを順番に渡す必要があります.var newArr = [10, 20, 30].map(function(currentValue, index) {
console.log(currentValue, index);
return currentValue + 5;
});
console.log(newArr);
// 출력값
// 10 0
// 20 1
// 30 2
// [15, 25, 35]
// ----------------------------------------------------------
// 인자의 순서를 지키지 않은 경우
var newArr2 = [10, 20, 30].map(function(index, currentValue) {
console.log(index, currentValue);
return currentValue + 5;
});
console.log(newArr2);
// 출력값
// 10 0
// 20 1
// 30 2
// [5, 6, 7]
this
コールバック関数も関数なので、デフォルトではグローバルオブジェクトを指しますが、コールバック関数に別のターゲットを指定すると、そのターゲットが参照されます.
コールバック関数の内部で別の値を参照する場合は、bind
メソッドを使用してこの値にバインドします.setTimeout(function() {
console.log(this);
}, 1000);
// Window { ... } 출력
document.body.innerHTML += '<button id="btn">Click</button>';
document.body.querySelector('#btn').addEventListener('click', function() {
console.log(this);
})
// <button id="btn">Click</button> 출력
// bind 메서드로 this 바인딩
var obj1 = {
name: 'obj1',
func: function() {
console.log(this.name);
}
}
setTimeout(obj1.func.bind(obj1), 1000);
var obj2 = { name: 'obj2' };
setTimeout(obj1.func.bind(obj2), 2000);
// 1초 후
// obj1 출력
// 1초 후
// obj2 출력
コールバック関数は関数です
コールバック関数を使用してオブジェクトを渡す方法を使用すると、メソッドではなく関数として呼び出されます.var obj = {
vals: [1, 2, 3],
logValues: function(value, index) {
console.log(this, value, index)
}
}
obj.logValues(1, 2); // { vals: [1, 2, 3], logValues: f} 1 2 출력
[4, 5, 6].forEach(obj.logValues); // Window { ... } 4 0 Window { ... } 5 1 Window { ... } 6 2 출력
アレイ高次関数
コールバック関数は、非同期処理だけでなく、高次関数を並べ替えるためにも使用されます.var map = [1, 2, 3].map(function(item) {
return item * 2;
});
console.log(map); // [2, 4, 6] 출력
var filter = [1, 2, 3].filter(function(item) {
return item % 2;
});
console.log(filter); // [1, 3] 출력
var reduce = [1, 2, 3].reduce(function(acc, cur) {
return acc + cur;
}, 0);
console.log(reduce); // 6 출력
コールバック地獄
コールバック関数を匿名関数に渡すプロセスを繰り返し、コードのインデントが深すぎます.
通常、非同期操作を実行するときに発生します.
⑥¥毒性が低いだけでなく、メンテナンスにも不利!loadScript('1.js', function(error, script) {
if (error) {
handleError(error);
} else {
// ...
loadScript('2.js', function(error, script) {
if (error) {
handleError(error);
} else {
// ...
loadScript('3.js', function(error, script) {
if (error) {
handleError(error);
} else {
// ...
}
});
}
})
}
});
callback地獄を解決する方法は?
var count = 0;
var timer = setInterval(function() { // setInterval 함수가 콜백 함수의 제어권을 넘겨받음.
console.log(count);
if(++count > 4) clearInterval(timer);
}, 1000);
// 1초 후
// 0
// 1초 후
// 1
// 1초 후
// 2
// 1초 후
// 3
// 1초 후
// 4
var newArr = [10, 20, 30].map(function(currentValue, index) {
console.log(currentValue, index);
return currentValue + 5;
});
console.log(newArr);
// 출력값
// 10 0
// 20 1
// 30 2
// [15, 25, 35]
// ----------------------------------------------------------
// 인자의 순서를 지키지 않은 경우
var newArr2 = [10, 20, 30].map(function(index, currentValue) {
console.log(index, currentValue);
return currentValue + 5;
});
console.log(newArr2);
// 출력값
// 10 0
// 20 1
// 30 2
// [5, 6, 7]
setTimeout(function() {
console.log(this);
}, 1000);
// Window { ... } 출력
document.body.innerHTML += '<button id="btn">Click</button>';
document.body.querySelector('#btn').addEventListener('click', function() {
console.log(this);
})
// <button id="btn">Click</button> 출력
// bind 메서드로 this 바인딩
var obj1 = {
name: 'obj1',
func: function() {
console.log(this.name);
}
}
setTimeout(obj1.func.bind(obj1), 1000);
var obj2 = { name: 'obj2' };
setTimeout(obj1.func.bind(obj2), 2000);
// 1초 후
// obj1 출력
// 1초 후
// obj2 출력
var obj = {
vals: [1, 2, 3],
logValues: function(value, index) {
console.log(this, value, index)
}
}
obj.logValues(1, 2); // { vals: [1, 2, 3], logValues: f} 1 2 출력
[4, 5, 6].forEach(obj.logValues); // Window { ... } 4 0 Window { ... } 5 1 Window { ... } 6 2 출력
var map = [1, 2, 3].map(function(item) {
return item * 2;
});
console.log(map); // [2, 4, 6] 출력
var filter = [1, 2, 3].filter(function(item) {
return item % 2;
});
console.log(filter); // [1, 3] 출력
var reduce = [1, 2, 3].reduce(function(acc, cur) {
return acc + cur;
}, 0);
console.log(reduce); // 6 출력
loadScript('1.js', function(error, script) {
if (error) {
handleError(error);
} else {
// ...
loadScript('2.js', function(error, script) {
if (error) {
handleError(error);
} else {
// ...
loadScript('3.js', function(error, script) {
if (error) {
handleError(error);
} else {
// ...
}
});
}
})
}
});
Reference
この問題について(JS|コールバック関数が返されます🪃), 我々は、より多くの情報をここで見つけました https://velog.io/@solseye/JS-콜백함수는-다시-돌아오는-거야テキストは自由に共有またはコピーできます。ただし、このドキュメントのURLは参考URLとして残しておいてください。
Collection and Share based on the CC Protocol