2015년 5월 17일 일요일

[JavaScript] Closure(클로져)

Closure(클로져) 란 무엇인가?


자바스크립트에서 클로져란(Closure) 다른 함수의 스코프(Scope)내에 있는 변수들에 접근할 수 있는 함수를 뜻한다. 아래 코드를 보자.


function closureExample(exVar){
  return function(){
    return exVar;
  };
}

var foo = closureExample("foo");
var bar = closureExample("bar");

console.log(foo());
console.log(bar());

closureExample이라는 함수는 매개변수로 exVar를 받으며, 내부에서 anonymous function(익명 함수, 람다 함수)을 선언 후 반환한다. 반환되는 함수 closureExample함수의 스코프에서 선언되었기 때문에 closureExample함수의 매개변수로 주어진 exVar이라는 변수에 접근할 수 있다. 그리고 반환된 익명 함수는 function expression 방식으로 foobar라는 변수에 어싸인되게 된다.

그렇게 foo와 bar 함수를 실행하면, closureExample함수로 전달한 매개변수에 접근하는 함수가 반환된게 된다.

이게 가능한 이유는 자바스크립트의 Execution Context가 다른 Execution Context에 의해 참조되는 한 파기되지 않기 때문이다. Execution Context 와 스코프에 대해 자세한 글을 읽어볼려면 여기를 클릭하자

조금 더 정확히 말하자면, 반환되는 익명함수는 호출된 closureExample함수내에서 선언되었기 때문에 closureExample함수의 Execution Contextvariable environment 객체를 참조하고 있는데, 자바스크립트의 가비지 콜랙터(Garbage Collector)는, 객체가 다른 인스턴스에 의해 참조되고 있는 동안은 해당 객체를 사용 중으로 판단하여 객체에 할당된 메모리를 수집하지 않는다.

closureExample 함수 내에서 선언된 익명함수 객체가 반환되면서 function expression 방식으로 foo라는 변수에 의해 참조되게 되는데, 이렇게 되면서, 해당 익명함수의 variable environment 객체는 사용 중으로 마크되며, 사용 중으로 마크된 익명함수의 execution context가 closureExample 함수의 variable environment 객체를 참조하게 되니, 마찬가지로 closureExample의 variable environment 객체도 사용중으로 마크되게 된다.

이 때문에, closureExmaple함수의 실행이 끝나 정해진값을 반환했음에도 우리는 closureExample이 호출될 때 생성된 variable environment에 계속 접근이 가능하다.



댓글 없음:

댓글 쓰기