this를 알아보자

  • 자바스크립트에서 this는 실행시에 결정된다.
console.log(this); // window

(function() {
    console.log(this); // window
})();

var test = function a() {
    console.log(this);
};
test(); // window

function outer() {
    return function inner() {
        console.log(this);
    }
}
var closure = outer();
closure(); // window


function createIterator(items) {
  let i = 0;
  return {
      next: function() {
      const done = (i >= items.length);
      const value = !done ? items[i++] : undefined;
      console.log('function!', this);
      return {
          done: done,
        value: value
      };
    }
  };
}

const iter = createIterator([1,2,3,4,5]);
iter.next(); // {next: f}
iter.next.call(null); // window

function getObj() {
  const items = ['banana', 'apple', 'orange'];
  return {
        getItems: function() {
          console.log(this);
          return this.items;
        },
        getItemsArrow: () => {
          console.log(this);
          return items;
        }
    };
}

var obj = getObj();

var items = obj.getItems(); // this => {getItems: f, getItemsArrow: f}
console.log(items); // undefined

items = obj.getItems;
items(); // this => window

items = obj.getItemsArrow(); // window
console.log(items);// ["banana", "apple", "orange"]

getObj.call({a : 'hi'}); //
getObj.call({a : 'hi'}).getItemsArrow(); // {a: "hi"}
getObj.call({a : 'hi'}).getItems(); // {getItems: ƒ, getItemsArrow: ƒ}
  • getObj가 실행될때 getObj함수 내에서 this가 {a: '11'} 이죠

  • 참고: Function.prototype.call

  • 그럼 위에서 this값이 위와 같이 결정되는지 알아보자

일단 화살표 함수는 선언되는 시점에 this가 결정되고 절대 안 바뀐다.

getObj.call({ a: 'hi' }); // 이 때 화살표 함수의 this는 { a: 'hi' }로 고정
getObj.call({ a: 'hi' }).getItemsArrow(); // 그래서 { a: 'hi' } 가 출력

반대로 일반 함수는 실행되는 시점에 this가 결정되기 때문에...

getObj.call({ a: 'hi' }); // { getItems: f, getItemsArrow: f } 리턴
getObj.call({ a: 'hi' }).getItems(); 
// getObj가 실행되는 시점의 this는 { a: 'hi' }가 되지만, 
// getItems()가 실행되는 시점의 this는 { getItems: f, getItemsArrow: f } 객체가 된다.
  • 마지막으로 return을 this.items와 items으로 할 경우 차이
    • this가 의미하는 것은 위에서 살펴본 것 처럼 각 상황에 따라 달라진다.
    • return items 같은 경우는 closure의 속성에 따라 getItems가 실행이 끝나도 내부함수에서 접근 가능하고 그 items 배열을 리턴할 수 있다.