본문 바로가기
javascript

js this (javascript this)가 가리키는 3가지

by 왜 안되지 2022. 3. 24.

먼저하는 요약

1. object 내의 method에서 쓰는 this 는 그 method 를 가지고 있는 object를 뜻한다.

2. constructor 안에서 쓰는 this 는 새로 생성되는 object 를 뜻한다.

3. 이벤트리스너 안에서의 this 는 e.currentTarget(지금 이벤트가 동작하는 곳) 을 뜻한다.

 

* 화살표 함수 내부의 this 는 값을 변화시키지 않고 외부의 this 값을 그대로 재사용한다.


1. object 내의 method 에서 쓰는 this 

object 내의 method에서 쓰는 this 는 그 method 를 가지고 있는 object를 뜻한다.

 

    <script>
      const obj = {
        data: 'kim',
        func: function () {
          console.log(this);
        },
      };
      obj.func(); // {data: 'kim', func: f}
      // object 안의 method 에서 this 는 그 함수를 가지고 있는 object
    </script>

 

 

우리가 global 함수를 만들면 사실 window 객체에 메서드를 만드는 것이므로

만약 globalFunc 라는 글로벌함수를 만든다면 우리는 이를 window.globalFunc() 라고 호출할 수 있다.

    <script>
      function globalFunc() {
        console.log('글로벌 함수는 사실 window 객체의 메서드입니다..');
      }
      globalFunc();
      window.globalFunc();
    </script>

 

 

따라서 글로벌 함수에서 this 는 메서드의 주인인 window 객체를 반환한다.

    <script>
      console.log(this);
    </script>

 

 

중첩된 객체의 내부 객체에서 this 는 무얼 가리킬까 ?

    <script>
      const obj = {   // 외부 객체
        data: {   //내부객체
          func: function () {
            console.log(this);
          },
        },
      };
      obj.data.func(); // {func: f}
      // 중첩 object 안의 method 에서 this 는 그 함수를 가지고 있는 object
      // 따라서 obj 객체가 아닌 data 객체가 출력됨.
    </script>

 

이것도 역시 this 가 해당 메소드를 가지고 있는 객체를 가리킨다.

따라서 obj 객체가 아닌 data 객체를 가리킨다.

 


2. constructor 안에서 쓰는 this

constructor 안에서 this 는 새로 생성되는 object (instance) 를 뜻한다.

 

    <script>
      function func() {
        this.name = 'kim'; //여기서 this 는 새로생성되는 오브젝트(instance)
        console.log(this);
      }
      const newobj = new func();
      console.log(newobj);
      // constructor 안에서 쓰면 새로 생성되는 오브젝트를 뜻함
    </script>


3. 이벤트리스너 안에서 쓰는 this

 

이벤트리스너 안에서의 this 는 e.currentTarget (지금 이벤트가 동작하는 곳) 을 뜻한다.

    <script>
      document.getElementById('button').addEventListener('click', function (e) {
        console.log(this); // 이벤트리스너 안에서의 this 는 e.currentTarget ( 지금 이벤트가 동작하는 곳)
        console.log(e.currentTarget); // <button id = 'button'>button</button>
      });
      // 이벤트리스너 안에서의 this 는 e.currentTarget(지금 이벤트가 동작하는 곳) 을 뜻함
    </script>

 

 


이런 경우는 어떨까?

 

case1. 이벤트 리스너 콜백함수 내부 forEach 함수의 콜백함수 안에서 this

 

    <script>
      document.getElementById('button').addEventListener('click', function (e) {
        const array1 = [1, 2, 3];
        array1.forEach(function (a) {
          console.log(this); // window => 이벤트리스너의 콜백함수안에서 forEach의 콜백함수는 전역함수이기때문
        });
      });
    </script>

 

 

비록 이벤트리스너 내부이지만 forEach 메서드는 window 전역객체의 메서드 이므로 forEach 의 콜백함수는 전역함수이다. 따라서 this 는 window 를 가리킨다.

 

 

 

case2. 객체 내에서 콜백함수를 쓸때의 this

    <script>
      const obj = {
        names: ['kim', 'lee', 'park'],
        func: function () {
          console.log(this); //---1   얘는 obj 객체를 출력
          obj.names.forEach(function () {
            console.log(this); //---2   얘는 window 출력
          });
        },
      };
      obj.func(); // forEach 의 콜백함수는 그냥 일반함수이기때문에 this 는 window 가 나옴
    </script>

1 번의 this 는 메서드의 주인인 obj 객체를 출력한다.

2 번의 this 는 forEach 의 콜백함수 내에서 this를 출력 했으므로 case1 과 같은 이유로 window 를 출력한다.

 

 


화살표 함수 내부의 this

arrow function 에서의 this 는 내부의 this 값을 변화시키지 않고 외부의 this 값을 그대로 재사용한다.

 

    <script>
      const obj = {
        data: {
          func: () => {
            console.log(this);
          },
        },
      };
      obj.data.func(); //window
      // arrow function 을 쓰면 this 는 window
    </script>

 

 

이런 화살표함수의 특성을 이용하면 bind, call,apply 등의 this 바인딩을 대체할수 있다.

 

    <script>
      const obj = {
        names: ['kim', 'lee', 'park'],
        func: function () {
          console.log(this); // 얘는 obj4를 출력
          obj.names.forEach(() => {
            console.log(this); // 얘도 obj4 출력
          });
        },
      };
      obj.func(); // 화살표 함수는 내부의 this 값을 변화시키지 않고 외부의 this 값을 그대로 재사용 한다.
    </script>

 

참고로 use strict 를 적용한 strict 모드에서는 일반 함수의 this 가 undefined 를 출력한다.

 

 

    <script>
      'use strict';
      console.log(this); // window
      function funct() {
        console.log(this);
      }
      funct(); // undefined
      // strict mode 에서는 그냥쓰면 this 가 window 일반함수내에서 쓰면 undefined
    </script>

 

댓글