함수 콜백패턴
- 퍼블리셔/javascript
- 2014. 6. 4. 06:00
콜백패턴
함수는 객체다. 즉 함수를 다른 함수의 인자로 전달할 수 있다.
introduceBugs()함수를 writeCode() 함수의 인자로 전달하면, 이때 introduceBugs()를 콜백함수 또는 간단하게 콜백이라고 부른다.
즉 함수를 다른 함수의 인자로 전달하면, 인자로 전달된 함수를 콜백함수라고 한다.
function writeCode(callback) {
// 어떤 작업을 한다.
callback();
// ...
}
function introduceBugs() {
// 버그를 만든다.
}
writeCode(introduceBugs);
introduceBugs()가 writeCode()의 인자로 괄호 없이 전달된 사실을 눈여겨 봐야한다.
괄호를 붙이면 함수가 실행되는데 이 경우는 함수의 참조만 전달하고 있다.
콜백예제를 설명하기 위해 긴 예제가 사용된다. 한번 사용하고 리팩토링해서 다시 사용한다.
findNodes 함수는 DOM 노드의 배열을 반환한다. hide() 함수는 노드를 숨긴다.
var findNodes = function () {
var i = 100000, // 긴루프
nodes = [], // 결과를 저장할 배열
found; // 노드 탐색 결과
while (i) {
i -= 1;
// 이 부분에 복잡한 로직이 들어간다
nodes.push(found);
}
return nodes;
};
var hide = function (nodes) {
var i = 0, max = nodes.length;
for (; i < max; i += 1) {
nodes[i].style.desplay = 'none';
}
};
// 함수실행
hide(findNodes());
아래의 에제는 fineNodes()에서 반환된 노드의 배열에 대해 hide()가 다시 루프를 돌아야하기 때문에 비효율적이다.
findNodes()에서 노드를 선택하고 바로 숨긴다면 재차 루프를 돌지 않아 더 효율적일 것이다.
그렇지만 findNodes()안에서 노드를 숨기는 로직을 구현하면 탐색과 수정 로직의 결합으로 인해 범유 함수의 의미가 퇴색될 것이다.
이때 바로 콜백 패턴을 사용한다. 노드를 숨기는 로직의 실행을 콜백 함수에 위임하고 이 함수를 findNodes()에 전달한다.
아래는 수정된 코드
// findNodes() 가 콜백을받도록 리팩터링한다.
var findNodes = function (callback) {
var i = 100000,
nodes = [],
found;
// 콜백 함수를 호출할 수 있는지 확인한다.
if (typeof callback !== 'function') {
callback = false;
}
while (i) {
i -=1;
// 이곳에 복잡한 로직을 구현한다.
// 여기서 콜백을 실행한다.
if (callback) {
callback(found);
}
nodes.push(found);
}
return nodes;
};
var hide = function (node) {
node.style.display = 'none';
}
// 노드를 찾아서 바로 숨긴다.
findNodes(hide);
이 방법은 직관적이다. findNodes()에는 콜백함수가 추가되었는지 확인하고, 있으면 실행하는 작업 하나만 추가되었다.
콜백은 생략할 수 있기 때문에 리팩터링된 findNodes()는 여전히 이전과 동일하게 사용할 수 있고, 기존 API에 의존하는 코드를 망가뜨리지 않는다.
출처 : JavaScript Patterns