์์ ์ด ์ํ ๊ฐ์ฒด, ์์ฑ๋ ์ธ์คํด์ค๋ฑ์ ๊ฐ๋ฆฌํค๋ ์ฐธ์กฐ๋ณ์์ด๋ค.
๐ก this๋ ํจ์ํธ์ถ ๋ฐฉ์์ ๋ฐ๋ผ์ ๋์ ์ผ๋ก ๊ฒฐ์ ๋๋ค.
๐ก this์ ๊ฐ๋ฆฌํค๋ ์ฐธ์กฐ๋ณ์๋ ํจ์ ํธ์ถ ์์ ์ ๊ฒฐ์ ๋๋ค.
ํจ์ํธ์ถ์ด๋ ๋ช ์์ ์ผ๋ก this๋ฅผ ์ง์ ํ์ฌ this๊ฐ ๊ฐ๋ฆฌํค๋ ์ฐธ์กฐ๋ณ์๋ฅผ ๊ฒฐ์ ํ๋ค. ์ด๊ฒ์ this ๋ฐ์ธ๋ฉ์ด๋ผ๊ณ ํ๋ค.
๐ก ์ผ๋ฐํจ์๋ก์ ํธ์ถ ๋ฐฉ์ => window ๊ฐ์ฒด
๐ก ๊ฐ์ฒด์ ๋ฉ์๋๋ก์์ ํธ์ถ => ๋ฉ์๋๋ก์ ํธ์ถํ ๊ฐ์ฒด
๐ก ์์ฑ์ํจ์๋ก ์์ฑํ ์ธ์คํด์ค ํธ์ถ => ์ธ์คํด์ค ๊ฐ์ฒด
๐ก ๋ช ์์ ํธ์ถ => function.prototype.[apply, call, bind]
โ Doc์์ Node๋ฅผ ํธ์ถํ๊ฑฐ๋ ์ด๋ฒคํธ๋ฅผ ์ฌ์ฉํ ๋ this๋ ํด๋น Node๋ฅผ ๊ฐ๋ฅดํจ๋ค.๐ 5-3 ์ผ๋ฐํจ์๋ก์์ this ํธ์ถ
function functionThis() { return this; } console.log(functionThis()); // window ์ถ๋ ฅ
์ด์ ๊ฐ์ด ์ผ๋ฐํจ์๋ก์์ ํธ์ถ์ this๋ ์ ์ญ๊ฐ์ฒด window๋ฅผ ๊ฐ๋ฆฌํจ๋ค.
var a = 10; // ์ ์ญ๋ณ์ a ์ ์ธ function functionThis() { return this.a; } console.log(functionThis()); // 10 ์ถ๋ ฅ
var๋ฅผ ์ฌ์ฉํ๋ฉด window๊ฐ์ฒด์์ a๋ฅผ ์ ์ธ๋์ด ์ฌ์ฉํ ์ ์๋ค.
const obj = { objThis : function() { return this; } } console.log(obj.objThis()); // obj ์ถ๋ ฅ
๊ฐ์ฒด์ ๋ฉ์๋๋ก์์ ํธ์ถ์ ํธ์ถํ ๊ฐ์ฒด๋ฅผ ๊ฐ๋ฆฌํจ๋ค.
const obj = { num : 10, objThis : function() { return this.num; } } console.log(obj.objThis()); // 10 ์ถ๋ ฅ
๊ฐ์ฒด์ ์ธ์๋ฅผ ์ฌ์ฉํ ์ ์๋ค.
function createFunction(num) { this.num = num; this.createFunctionThis = function() { return this; } } const instance1 = new createFunction(10); const instance2 = new createFunction(20); console.log(instance1.createFunctionThis()); // instance1 ์ถ๋ ฅ console.log(instance2.createFunctionThis()); // instance2 ์ถ๋ ฅ // ์์ฑ์ ํจ์๋ก ์ธํด์ ๋ง๋ค์ด์ง ์๋ก์ด ๊ฐ์ฒด์ด๊ธฐ ๋๋ฌธ์ ๋ค๋ฅธ this๋ฅผ ๊ฐ์ง๋ค. console.log(instance1 === instance2); // false ์ถ๋ ฅ
์์ฑ์ํจ์๋ก ๋ง๋ ์ธ์คํด์ค๋ก์์ this๋ ์ธ์คํด์ค๋ ๊ฐ๋ฆฌํจ๋ค.
function createFunction(num) { this.num = num; this.createFunctionThis = function() { return this.num; } } const instance1 = new createFunction(10); const instance2 = new createFunction(20); console.log(instance1.createFunctionThis()); // 10 ์ถ๋ ฅ console.log(instance2.createFunctionThis()); // 20 ์ถ๋ ฅ
์ธ์คํด์ค์ ์ธ์๋ฅผ ์ฌ์ฉํ ์ ์๋ค.
๐ function.prototype.apply(์ฌ์ฉํ this ๊ฐ์ฒด, [ํจ์์ธ์])
const obj = { num : 10 } function applyThis() { return this; } console.log(applyThis.apply(obj)); // { num : 10 } ์ถ๋ ฅ
this๊ฐ obj๋ฅผ ๊ฐ๋ฆฌํค๋๋ก ๋ฐ์ธ๋ฉ ๋์๋ค.
const obj = { num1 : 10 } function applyThis(a, b) { const num2 = a; const num3 = b; return this.num1 + num2 + num3; } console.log(applyThis.apply(obj, [10, 20])); // 40 ์ถ๋ ฅ
์ด์ฒ๋ผ ์๋๋ window๊ฐ์ฒด๋ฅผ ๊ฐ๋ฆฌํค๋ this๋ฅผ ๋ช ์์ ์ผ๋ก obj๋ฅผ ๊ฐ๋ฆฌํค๋๋ก ๋ฐ์ธ๋ฉ๋์๋ค.
๐ function.prototype.call(์ฌ์ฉํ this ๊ฐ์ฒด, ํจ์์ธ์)
const obj = { num : 10 } function callThis() { return this; } console.log(callThis.call(obj)); // { num : 10 } ์ถ๋ ฅ
this๊ฐ obj๋ฅผ ๊ฐ๋ฆฌํค๋๋ก ๋ฐ์ธ๋ฉ ๋์๋ค.
const obj = { num1 : 10 } function callThis(a, b) { const num2 = a; const num3 = b; return this.num1 + num2 + num3; } console.log(callThis.call(obj, 10, -5)); // 15 ์ถ๋ ฅ
apply์ ๋๊ฐ์ด ์๋๋ window๊ฐ์ฒด๋ฅผ ๊ฐ๋ฆฌํค๋ this๋ฅผ ๋ช ์์ ์ผ๋ก obj๋ฅผ ๊ฐ๋ฆฌํค๋๋ก ๋ฐ์ธ๋ฉ๋์๋ค.
๐ function.prototype.bind(์ฌ์ฉํ this ๊ฐ์ฒด, ํจ์์ธ์)
const obj = { num : 10 } function bindThis() { return this; } console.log(bindThis.bind(obj)); // bindthis ์ถ๋ ฅ
apply์ call๊ณผ๋ ๋ค๋ฅด๊ฒ bindThis ํจ์๊ฐ ์ถ๋ ฅ๋๋ค. ํจ์๋ฅผ ์ฌ์ฉํ๊ธฐ ์ํด์ ๋ณ์์ ๋ฃ์ด์ค์ ์คํ์ ํด์ผํ๋ค.
const obj = { num : 10 } function bindThis() { return this; } const bindStart = bindThis.bind(obj); console.log(bindStart()); // { num : 10 } ์ถ๋ ฅ
์ด์ ๊ฐ์ด ํจ์๋ฅผ ์คํํด์ค์ผ ํ๋ค.
const obj = { num1 : 10 } function bindThis(a, b) { const num2 = 10; const num3 = 20; return this.num1 + num2 + num3; } const bindStart = bindThis.bind(obj); console.log(bindStart()); // 40 ์ถ๋ ฅ
call๊ณผ apply๋ ํจ์์ ์ธ์๋ฅผ ๋ฃ๋ ๋ถ๋ถ์ด ๋ค๋ฅด์ง๋ง this๋ฅผ ํน์ ๊ฐ์ผ๋ก ์ง์ ํ๋ ๊ฒ์ด๋ค. ํ์ง๋ง bind๋ ํจ์์ this์ ๊ฐ์ ์๊ตฌ์ ์ผ๋ก ๋ฐ๊ฟ์ ์ฌ์ฉํ ์ ์๋ค.
var name = 'KIM'; // window ๊ฐ์ฒด name ์ ์ธ const obj = { name : 'LEE', info : function(callback) { // callback ํจ์์ ์คํ๊ฐ์ ๋ฐํ return callback(); } } // callback function function callback() { return `${this.name}์ ๋์ด๋ 20์ด ์ ๋๋ค.`; } // obj์์ ์๋ info ๋ฉ์๋์์ ์ฝ๋ฐฑํจ์๋ฅผ ์คํํ๋ค. console.log(obj.info(callback)); // KIM์ ๋์ด๋ 20์ด ์ ๋๋ค. ์ถ๋ ฅ
์ด์ ๊ฐ์ด ์๋ํ๋ฉด window ๊ฐ์ฒด์ ์ ๊ทผํ์ฌ name์ ์ฝ์ด์๋ค. ์๋ํ๋ฉด info๋ ๋ฉ์๋๋ก์์ ํธ์ถ์ด ๋์ด info์ this๋ obj๋ฅผ ๊ฐ๋ฆฌํค์ง๋ง callback์ info์์์ ์ผ๋ฐํจ์๋ก ํธ์ถ์ด ๋์ด์๋ค. ๊ทธ๋ฌ๋ฏ๋ก this๋ ์ผ๋ฐํจ์์ ์คํ์ฒ๋ผ window๋ฅผ ๊ฐ๋ฆฌํค๊ฒ ๋๋ค.
var name = 'KIM'; const obj = { name : 'LEE', info : function(callback) { // callback ํจ์์ bind this๋ฅผ ํด์ค๋ค. const bindObj = callback.bind(this); // ๋ช ์์ ์ผ๋ก ๋ณํ๋ bindObj๊ฐ ์ถ๋ ฅ return bindObj(); } } function callback() { return `${this.name}์ ๋์ด๋ 20์ด ์ ๋๋ค.`; } console.log(obj.info(callback)); // LEE์ ๋์ด๋ 20์ด ์ ๋๋ค.
bind์ this๋ง ๋ฃ์ด์ค ์ด์ ๋ info๋ ๊ฐ์ฒด์ ๋ฉ์๋๋ก์์ ํธ์ถ์ด ๋์ด์๊ธฐ ๋๋ฌธ์ this๊ฐ obj๋ฅผ ๊ฐ๋ฆฌํค๊ณ ์๋ ์ํ์ด๋ค. ๊ทธ ๊ฐ๋ฆฌํค๋ this๋ฅผ ๋ช ์์ ์ผ๋ก ๋ฐ์ธ๋ฉ ํด์ฃผ๋ฉด window ๊ฐ์ฒด๋ฅผ ๊ฐ๋ฆฌํค๋ callback ํจ์์ ๋ฐ์ธ๋ฉ ํ์ฌ bindObj ํจ์์ this๋ obj๋ฅผ ๊ฐ๋ฆฌํค๊ฒ ๋๋ค. ์ด์ฒ๋ผ this๋ ํจ์ํธ์ถ ๋ฐฉ์๊ณผ ํธ์ถ์์ ์์ ๋์ ์ผ๋ก ๋ณํํ๊ฒ ๋๋ค.