this 는 자신이 속한 객체 또는 어떤 값을 가리키는 자기 참조 변수입니다.
비엄격 모드
function test() {
return this
}
console.log( test() === window ); // true 출력
비엄격 모드에서 this 는 항상 객체를 참조하게 되어 있습는다. 그런데 this 가 있는 test 함수는 객체가 아니기 때문에 전역객체 window 를 참조합니다. (nodejs 에서는 global 참조)
엄격 모드
function test() {
"use strict"; // 엄격모드 선언
return this
}
console.log(test() === undefined); // true 출력
엄격모드에서 this 는 어떤 값이든 설정이 가능합니다. test 함수를 실행할때 this 에대한 설정 없기 때문에 this 는 undefined 로 지정됩니다.
객체와 함수
const obj = {
name: 'jh',
test: function () {
return this;
},
}
console.log( obj.test() ); // obj 출력
var fn = obj.test; // this 재설정
console.log(fn() === window); // true 출력
this 의 위치가 obj 객체 안에 있기 때문에 비엄격 / 엄격 모드 상관 없이 obj 객체를 참조합니다. 위에 11 번 코드를 보면 test 함수를 바로 호출하지 않고 fn 으로 할당하게 됩니다. 이때 obj 안에 있는 함수가 아닌 전역(Global)에 있는 함수로 바뀌기 때문에 this 는 비엄격 모드에서는 window, 엄격 모드에서는 undefined 를 참조하게 됩니다.
function addition() {
return this.name;
}
obj.add = addition; // this 재설정
console.log( obj.add() ); // jh 출력
addition 에 있는 this 는 비엄격 모드에서 전역객체 window, 엄격 모드에서는 undefined 를 가리키게 되어 있지만, obj.add 에 할당하면서 this 는 obj 를 가리키게 됩니다.
this 설정하기
const obj = {
name: 'jh',
}
function test() {
return this
}
console.log( test.call( obj ) ); // obj 출력
console.log( test.apply( obj ) ); // obj 출력
console.log( test.bind( obj )() ); // obj 출력
call(), apply(), bind() 를 통해서 this 를 설정할 수 있습니다.
- call : 첫번째 인자를 this 로 설정, 나머지를 인자값으로 넘김
- apply : 첫번째 인자를 this 로 설정, 두번째 인자를 배열로 넘김
- bind : 첫번째 인자를 this 로 설정, 바로 실행하지 않고 함수를 리턴, 함수를 실행할때 인자값을 넘김
function test() {
return this
}
console.log( test.call() === window ); // true 출력
console.log( test.call('string') ); // [String: 'string'] 출력
console.log( test.call(3) ); // [Number: 3] 출력
비엄격 모드에서 this 설정이 객체가 아니면 객체로 변환 해줍니다.
function test() {
"use strict";
return this
}
console.log(test.call() === undefined); // true 출력
console.log(test.call('string')); // string 출력
console.log(test.call(3)); // 3 출력
엄격 모드에서는 this 에 값 그대로를 설정합니다.
function test() {
return this
}
console.log( test.bind( 3 )() ); // 3 출력
console.log( test.bind( 3 ).bind( 6 )() ); // 3 출력
console.log( test.bind( 3 ).bind( 6 ).bind( 9 )() ); // 3 출력
bind 는 this 를 최초 한번만 설정합니다.
DOM 이벤트와 this
function changeColor(e) {
// this == e.target or this == e.currentTarget
this.style.backgroundColor = 'red';
}
var elements = document.getElementsByTagName('p');
[...elements].forEach(element => element.addEventListener('click', changeColor));
함수를 이벤트 처리기로 사용하면 this는 이벤트를 발사한 요소로 설정됩니다. this 는 이벤트를 발사한 요소인 p 태그 엘리먼트를 가리키게 됩니다.
<button onclick="alert(this.tagName);">
버튼
</button>
인라인 코드도 마찬가지로 onclick 이벤트를 통해 발사한 요소인 button 을 가리키게 됩니다.
<button onclick="alert((function() { return this; })());">
버튼
</button>
위의 경우, 내부 함수의 this 는 정해지지 않았으므로 전역객체 window 를 반환합니다.
참고
https://developer.mozilla.org/ko/docs/Web/JavaScript/Reference/Operators/this
댓글