JS. this와 bind, call, apply

this

this 키워드는 생성자 함수 혹은 메소드에서 객체를 가리킬 때 사용하는 키워드이다.

1. 일반 함수에서의 this

일반 함수에서의 this는 window 객체를 가리킨다.

function foo() {
  console.log(this);  // 'this' === global object
};

foo();

Strict Mode

엄격 모드라 하며 여러가지 오류, 개발자의 실수를 보완해주기 위해 엄격한 코드실행 환경을 제공한다.

MDN - Strict Mode

'use strict';

var name = 'jkun';

function foo() {
  console.log(this.name); // 'this' === undefined
};

foo();

엄격 모드에서는 일반 함수 내의 this는 undefined를 반환한다.

var age = 100;

function foo() {
  var age = 99;
  bar();
};

function bar() {
  console.log(this.age);
};

foo();

bar 함수는 일반 함수 실행 방식이기에 this는 window 객체를 가리킨다.

2. Method에서의 this

var age = 100;

var obj = {
  age: 27,
  foo: function () {
    console.log(this.age);
  }
};

obj.foo();

Method에서 this는 Method를 호출한 객체를 가리킨다.

즉, 위 obj.foo()를 호출 했을 때, this는 foo 앞의 obj를 가리킨다.

3. 생성자 함수에서의 this

var Person = function(name, age) {
  this.name = name;
  this.age = age;
  // Method
  this.getName = function() {
    console.log(this.name);
  }
};

var person = new Person('jkun', 27);
console.log(person.name)  // 'jkun'
console.log(person.age)   // 27
console.log(person.getName()) // 'jkun'

Person 생성자 함수를 통해 person이라는 새로운 객체를 만들어 this는 person을 바인딩시킨다.

4. 내부 함수에서의 this

var x = 100;

function outer() {
  var x = 99;

  function inner() {
    console.log(this.x)
  };

  inner();

  console.log(x); // x = 99;
  console.log(this.x) // x = 100;
};

outer();

내부 함수 또한 일반 함수 실행 방식이기에 this는 global 즉, window 객체를 가리킨다.

var age = 30;
var person = {
  name: 'yilpe',
  age: 27,
  getPerson: function() {
    console.log(this.name); // name = 'yilpe';
    function getAge() {
      console.log(this);  // window
      console.log(this.age);  // age = 30;
    }

    getAge();
  }
};

위 예제는 메소드 안의 내부 함수이다. 메소드 안의 내부 함수의 this 또한 window 객체를 가리키는걸 볼 수 있다.

bind

bind 메소드는 this의 문맥을 유지할 때 사용한다.

var module = {
  x: 20,
  getX: function() {
    return this.x;  // x = 20;
  }
}

var otherGetX = module.getX;
console.log(otherGetX());  // undefined;

var anotherGetX = otherGetX.bind(module);
console.log(anotherGetX()); // x = 20;

bind 메소드를 사용하면 this를 원하는값으로 설정할 수 있다.

call, apply

callapply는 대게 함수의 arguments를 조작할 때 사용한다.

call 메소드는 this 인자와 함수의 인자와 같은 방식으로 인자를 받는다.

apply 메소드는 this인자와 배열 인자 총 2개의 인자만을 받는다.

var age = 27;

function foo () {
  console.log(this.age);
  console.log(arguments);
  console.log(typeof Array.prototype.join.call(arguments));
};

var obj = {
  age: 30
}

foo.call(obj, 1, 2, 3, 4, 5);
foo.apply(obj, [1, 2, 3, 4, 5]);

arguments는 함수의 숨겨진 속성으로 유사 배열로 배열의 메소드를 쓸 수 없다. 이에 arguments에 배열 메소드를 쓰기 위해 call과 apply를 사용한다.

bind VS apply, call

bind는 함수를 선언할 때, this와 파라미터를 지정해줄 수 있으며, callapply는 함수를 호출할 때, this와 파라미터를 지정해준다.

apply VS bind, call

apply 메소드에서는 첫번째 인자로 this를 넘겨주고 두번째 인자로 배열의 형태로 파라미터로 전달한다. bind메소드와 call메소드는 각각의 파라미터를 하나씩 넘겨준다.


Written by@Jkun
...

GitHub