[Javascript] 상황에 따라 달라지는 this

우지끈·2024년 10월 15일
post-thumbnail

다른 객체지향 언어에서의 this는 곧 클래스로 생성한 인스턴스를 말한다. 그러나 자바스크립트에서는 this가 어디에서나 사용될 수 있다. 실습 중 헷갈렸던 예제를 기반으로 this가 상황별로 어떻게 달라지는지를 확인해보고자 한다.

var fullname = 'Ciryl Gane'

var fighter = {
    fullname: 'John Jones',
    opponent: {
        fullname: 'Francis Ngannou',
        getFullname: function () {
            return this.fullname;
        }
    },

    getName: function() {
        return this.fullname;
    },

    getFirstName: () => {
        return this.fullname.split(' ')[0];
    },

    getLastName: (function() {
        return this.fullname.split(' ')[1];
    })()

}

console.log('Not', fighter.opponent.getFullname(), 'VS', fighter.getName());
console.log('It is', fighter.getName(), 'VS', fighter.getFirstName(), fighter.getLastName);

해당 코드를 콘솔에 입력하여 실행하면 어떤 결과가 나올지 예측해보자.

  1. fighter.opponent.getFullname()의 경우 호출 주체가 fighter.opponent.로 명확한 메서드임을 알 수 있다. 따라서 해당 블럭의 fullnameFrancis Ngannou가 오게 된다.

  2. fighter.getName() 이또한 fighter.로 호출 주체가 명확하다. 따라서 fighter 블럭의 full nameJohn Jones가 오게 될 것이다.

  3. console.log 두 번째 줄의 fighter.getName()은 2번과 동일하기에 John Jones가 그대로 오게 될 것이다.

  4. fighter.getFirstName(), fighter.getLastName 이 부분이 조금 복잡하다.
    4.1. fighter.getFirstName() : getFirstName은 화살표 함수이다. 화살표 함수는 ThisBinding을 하지 않기 때문에 자동적으로 상위의 this를 참조하게 된다. 따라서 마지막으로 ThisBinding이 이루어졌던 Ciryl Gane의 첫 번째 이름인 Ciryl을 split을 통해 가져오게 된다.
    4.2. fighter.getLastName : 우선 위의 다른 번호들과 다르게 혼자만 호출부가 없는 것을 확인할 수 있다. 따라서
    이 부분 함수를 통째로 가져오게 된다.
    해당 부분을 살펴보면, 스스로 선언하고 호출까지 바로 이루어지고 있음을 알 수 있다. 따라서 명확한 호출 주체가 없기에 전역 객체를 참조하게 된다. 따라서 Ciryl Gane의 두 번째 이름인 Gane을 split을 통해 가져오게 될 것이다.

최종 출력 결과

Not Francis Ngannou VS John Jones
It is John Jones VS Ciryl Gane

0개의 댓글