this๋ JAVA์์ ์์ ์ ๊ฐ๋ฅดํค๊ฑฐ๋ ์์ ์ด ์์ฑํ ์ธ์คํด์ค๋ฅผ ๊ฐ๋ฅดํค๋ ์๊ธฐ ์ฐธ์กฐ ๋ณ์์ด๋ค.
ํ์ง๋ง, JavaScript์์์ this๋ ํจ์ ํธ์ถ ๋ฐฉ์์๋ฐ๋ผ ๋ฌ๋ผ์ง๋ค.
๐๐ปโโ๏ธ this๋?
- JAVA
- ์์ ์ด ์ํ ๊ฐ์ฒด ๋๋ ์์ ์ด ์์ฑํ ์ธ์คํด์ค๋ฅผ ๊ฐ๋ฅดํค๋ ์๊ธฐ ์ฐธ์กฐ ๋ณ์์ด๋ค.- JavaScript
- this๋ ๊ธฐ๋ณธ์ ์ผ๋กwindow
๋ค.
- ํจ์ ํธ์ถ ๋ฐฉ์์ ๋ฐ๋ผ this๊ฐ ๊ฐ๋ฆฌํค๋ ๊ฐ์ฒด(this์ ๋ฐ์ธ๋ฉ๋๋ ๊ฐ์ฒด)๋ ๋ฌ๋ผ์ง ์ ์๋ค.
๐ ๋ฐ์ธ๋ฉ์ ๋ญ๊น?
- ๋ฐ์ธ๋ฉ์ this์ this๊ฐ ๊ฐ๋ฆฌํฌ ๊ฐ์ฒด๋ฅผ ์ฐ๊ฒฐํ๋ ๊ฒ์ ๋งํ๋ค.
โ ํจ์ ํธ์ถ ๋ฐฉ์์ ๋ฐ๋ผ this๊ฐ ๋ฌ๋ผ์ง๋ ์ด์
- this๋ ์คํ ์ปจํ ์คํธ๊ฐ ์์ฑ(์ค์ฝํ์ฒด์ธ, ๋ณ์ ๊ฐ์ฒดํ, this๋ฐ์ธ๋ฉ)๋ ๋ ๊ฒฐ์ ๋๋ค.
- ์ผ๋ฐ์ ์ผ๋ก ํจ์๋ฅผ ํธ์ถํ ๋ ์คํ ์ปจํ ์คํธ๊ฐ ์์ฑ๋๊ธฐ ๋๋ฌธ์, this๋ ํจ์๋ฅผ ํธ์ถํ ๋ ๊ฒฐ์ ๋๋ค๊ณ ํ ์ ์๋ค.
ํจ์ ํธ์ถ ๋ฐฉ์์ ์๋์ ๊ฐ์ด 4๊ฐ์ง๋ก ๋ถ๋ฅํด ๋ณผ ์ ์๋ค.
const foo = function() {
console.dir(this);
}
foo(); // this๋ window
const foo = function() {
console.dir(this);
}
const obj = {
foo : foo
};
obj.foo(); // this๋ obj
- JavaScript์์ ๋ชจ๋ ํจ์๋ ์์ฑ์ ํจ์์ด๊ธฐ๋ ํ๋ค.
- ํจ์ ํธ์ถ ์ new๋ฅผ ๋ช ์ํ๋ฉด, ํด๋น ํจ์(
instance
)๋ ๊ฐ์ฒด๋ฅผ ๋ฐํํ๊ณ , ์์ฑ์ ํจ์(foo
)๋ด๋ถ์์ ์ฌ์ฉ๋ this๋ ๋ฐํ๋ ๊ฐ์ฒด(instance
)๋ฅผ ๊ฐ๋ฅดํค๊ฒ ๋๋ค.
const foo = function() {
console.dir(this);
}
const instance = new foo(); // this๋ instance
apply
/call
ํธ์ถconst foo = function() {
console.dir(this);
}
const bar = {
name : 'bar'
};
foo.apply(bar); // this๋ bar
foo.call(bar); // this๋ bar
- ๊ธฐ๋ณธ์ ์ผ๋ก this๋ ์ ์ญ๊ฐ์ฒด(Global Object)์ ๋ฐ์ธ๋ฉ๋๋ค.
- ์ ์ญ๊ฐ์ฒด(Global Object)
- ๋ชจ๋ ๊ฐ์ฒด์ ์ ์ผํ ์ต์์ ๊ฐ์ฒด
- Browser-side(๋ธ๋ผ์ฐ์ ):
window
๊ฐ์ฒด- Server-side(Node.js):
global
๊ฐ์ฒด
์ ์ญํจ์๋ ๋ฌผ๋ก ๊ทธ ๋ด๋ถํจ์๊น์ง ์ ์ญ๊ฐ์ฒด์ ๋ฐ์ธ๋ฉ๋๋ค.
function foo() {
console.log(this); // this๋ window
function bar() {
console.log(this); // this๋ window
}
bar();
}
foo();
๋ฉ์๋์ ๋ด๋ถํจ์ ์ญ์ this๋ ์ ์ญ๊ฐ์ฒด์ ๋ฐ์ธ๋ฉ๋๋ค.
๐๐ปโโ๏ธ ๋ฉ์๋๋?
- ๊ฐ์ฒด๋ ํค(key)์ ๊ฐ(value)์ผ๋ก ๊ตฌ์ฑ๋ ํ๋กํผํฐ(property)์ ์งํฉ์ ๋๋ค.
- ์ด ํ๋กํผํฐ์ ๊ฐ์ผ๋ก ํจ์๊ฐ ์ฌ ์๋ ์๋๋ฐ, ์ด๋ฌํ ํ๋กํผํฐ๋ฅผ ๋ฉ์๋(method)๋ผ๊ณ ํฉ๋๋ค.
let value = 1;
let obj = {
value: 100,
foo: function() {
console.log(this); // this๋ obj
console.log(this.value); // this.value๋ 100
function bar() {
console.log(this); // this๋ window
console.log(this.value); // this.value๋ 1
}
bar();
}
};
obj.foo();
์ฝ๋ฐฑํจ์๋ this๋ ์ ์ญ๊ฐ์ฒด์ ๋ฐ์ธ๋ฉ๋๋ค.
๐๐ปโโ๏ธ ์ฝ๋ฐฑํจ์๋?
๋ค๋ฅธ ํจ์์ ์ธ์๋ก์ ์ด์ฉ๋๋ ํจ์
let value = 1;
let obj = {
value: 100,
foo: function() {
setTimeout(function() { // ์ฝ๋ฐฑํจ์
console.log(this); // this๋ window
console.log(this.value); // this.value๋ 1
}, 100);
}
};
obj.foo();
this
๊ฐ ์ ์ญ๊ฐ์ฒด๋ฅผ ์ฐธ์กฐํ๋ ๊ฒ์ ํผํ๋ ๋ฐฉ๋ฒ
- ์ธ๋ถํจ์์์ ์ธ๋ถํจ์๊ฐ ๊ฐ๋ฅดํค๋ this๋ฅผ ๋ณ์์ ๋ด๊ณ , ๋ด๋ถํจ์์์ ์ฐธ์กฐํ ์ ์๋๋กํ๊ธฐ
- JavaScript๊ฐ ์ ๊ณตํ๋
apply
,call
๋ฉ์๋ ์ฌ์ฉํ๊ธฐ
let value = 1;
let obj = {
value: 100,
foo: function() {
let that = this; // this === obj
console.log(this); // obj
console.log(this.value); // 100
function bar() {
console.log(this); // window
console.log(this.value); // 1
console.log(that); // obj
console.log(that.value); // 100
}
bar();
}
};
obj.foo();
๋ฉ์๋ ๋ด๋ถ์ this๋ ํด๋น ๋ฉ์๋๋ฅผ ์์ ํ ๊ฐ์ฒด, ์ฆ ํด๋น ๋ฉ์๋๋ฅผ ํธ์ถํ ๊ฐ์ฒด์ ๋ฐ์ธ๋ฉ๋๋ค.
let obj1 = {
name: 'Lee',
sayName: function() { // ๋ฉ์๋
console.log(this.name); // this === obj1
}
}
let obj2 = {
name: 'Kim'
}
obj2.sayName = obj1.sayName;
// obj2์ sayName ์์ฑ
// let obj2 = {
// name: 'Kim',
// sayName: function() {
// console.log(this.name); // this === obj2
// }
// }
obj1.sayName(); // Lee
obj2.sayName(); // Kim
ํจ์๋ฅผ ํธ์ถํ ๋, ํธ์ถํ๋ ํจ์๊ฐ ๊ฐ์ฒด์ ๋ฉ์๋์ธ์ง ๊ทธ๋ฅ ํจ์์ธ์ง์ ๋ฐ๋ผ this๊ฐ ๋ฌ๋ผ์ง๋ค.
let obj1 = {
sayName: function() {
console.log(this);
}
}
obj1.sayName(); // obj1
let newSayName = obj1.sayName;
newSayName(); // window
ํ๋กํ ํ์ ๊ฐ์ฒด ๋ฉ์๋ ๋ด๋ถ์ this ์ญ์ ์ผ๋ฐ ๋ฉ์๋์ ๋ง์ฐฌ๊ฐ์ง๋ก ํด๋น ๋ฉ์๋๋ฅผ ํธ์ถํ ๊ฐ์ฒด์ ๋ฐ์ธ๋ฉ๋๋ค.
// ์์ฑ์ ํจ์
function Person(name) {
this.name = name;
}
Person.prototype.getName = function() {
return this.name;
}
let me = new Person('Lee');
console.log(me.getName()); // Lee
Person.prototype.name = 'Kim';
console.log(Person.prototype.getName()); // Kim
์์ฑ์ ํจ์์ ์ญํ ์ ๊ฐ์ฒด๋ฅผ ์์ฑํ๋ ๊ฒ
์ด๋ค.
new
์ฐ์ฐ์๋ฅผ ๋ถ๋ฌ ํธ์ถํ๊ธฐnew
์ฐ์ฐ์์ ํจ๊ป ์์ฑ์ ํจ์๋ฅผ ํธ์ถํ์ง ์์ผ๋ฉด ์์ฑ์ ํจ์๋ก ๋์ํ์ง ์๋๋ค.// ์์ฑ์ ํจ์
function Person(name) {
this.name = name;
}
let me = new Person('Lee'); // new ์ฐ์ฐ์ ์ฌ์ฉ
console.log(me); // Person {name: "Lee"}
let you = Person('Kim'); // new ์ฐ์ฐ์ ์ฌ์ฉ์ํจ
console.log(you); // undefined
apply
/call
ํธ์ถ
- this ๋ฐ์ธ๋ฉ
- ์๋ฌต์ this ๋ฐ์ธ๋ฉ : ํจ์ ํธ์ถ ๋ฐฉ์์ ๋ฐ๋ผ ๊ฒฐ์ ๋จ
- ๋ช ์์ this ๋ฐ์ธ๋ฉ :
apply
/call
๋ฉ์๋- this๋ฅผ ์ด๋ค ๊ฐ์ฒด๋ก ์ง์ ํ ๊ฒ์ธ๊ฐ๋ฅผ ๋ช ์์ ์ผ๋ก ์ ํ ์ ์๋ค.
- ์ด ๋ฉ์๋๋ค์ ๋ชจ๋ ํจ์ ๊ฐ์ฒด์ ํ๋กํ ํ์ ๊ฐ์ฒด์ธ
Function.prototype
๊ฐ์ฒด์ ๋ฉ์๋์ด๋ค.
๐๐ปโโ๏ธ apply
function.apply(thisArg, [argsArray])
thisArg
: ํจ์ ๋ด๋ถ์ this์ ๋ฐ์ธ๋ฉํ ๊ฐ์ฒด[argsArray]
: ํจ์์ ์ ๋ฌํ argument์ ๋ฐฐ์ด
let Person = function (name1, name2) {
this.name1 = name1;
this.name2 = name2;
};
let foo = {};
Person.apply(foo, ['name1', 'name2']);
console.log(foo); // { name1: 'name1'; name2: 'name2' }
๐ ์คํ ๊ณผ์
1.apply()
๋ฅผ ํตํด Person ํธ์ถ
-apply()
๋ this๋ฅผ ํน์ ๊ฐ์ฒด์ ๋ฐ์ธ๋ฉํ ๋ฟ์ด๋ค.
- ๋ณธ์ง์ ์ธ ๊ธฐ๋ฅ์ ํจ์๋ฅผ ํธ์ถํ๋ ๊ฒ!
2. this์ ๊ฐ์ฒด foo๋ฅผ ๋ฐ์ธ๋ฉํจ
3. Person ํจ์์ this๋ foo ๊ฐ์ฒด๊ฐ ๋จ
4. Person ํจ์์ this์ ๋ฐ์ธ๋ฉ๋ foo ๊ฐ์ฒด์ name ํ๋กํผํฐ๊ฐ ์ถ๊ฐ๋๊ณ , ๊ฐ์ด ํ ๋น๋จ
๐๐ปโโ๏ธ call
apply์ ๊ฐ์ ๊ธฐ๋ฅ์ผ๋ก, ๊ทธ ๋ชจ์๋ง ๋ค๋ฅด๋ค.Person.apply(foo, ['name1', 'name2']); Person.call(foo, 'name1', 'name2');
let Person = function (name1, name2) {
this.name1 = name1;
this.name2 = name2;
};
let foo = {};
Person.call(foo, 'name1', 'name2');
console.log(foo); // { name1: 'name1'; name2: 'name2' }
๐๐ปโโ๏ธ this์ ์ฉ๋ฒ์ ์๋๋๋ก ์ค๋ช ํด์ฃผ์ธ์.
- ์คํ์ปจํ ์คํธ๋ ํจ์๊ฐ ํธ์ถ๋ ๋ ์์ฑ๋๋ค.
- this๋ ํจ์์ ์คํ์ปจํ ์คํธ๊ฐ ์์ฑ๋ ๋ ๊ฒฐ์ ๋๋ค.
- ๊ทธ ์ด์ ๋ ํจ์๊ฐ ํธ์ถ๋ ๋ ํจ์ ์ปจํ ์คํธ๊ฐ ์์ฑ๋๊ธฐ ๋๋ฌธ์ด๋ค.
- ํจ์์ ํธ์ถ ๋ฐฉ๋ฒ์ ์๋์ ๊ฐ์ด ํฌ๊ฒ 4๊ฐ์ง์ด๋ฉฐ, ์ด๋๋ง๋ค this๊ฐ ๊ฐ๋ฅดํค๋ ๊ฐ์ฒด๋ ๋ค๋ฅด๋ค.
- ์ ์ญ๋ฒ์์์์ ํจ์ ํธ์ถ (window)
- ๋ฉ์๋ ํธ์ถ (๋ฉ์๋๊ฐ ์ํ ๊ฐ์ฒด)
- ์์ฑ์ ํจ์ ํธ์ถ (์ธ์คํด์ค)
- apply / call ํธ์ถ (this๋ฐ์ธ๋ฉํ ๊ฐ์ฒด ์ค์ )
์ด ๊ธ์ ์๋์ ๊ธ์ ๋ฐํ์ผ๋ก ๊ณต๋ถํ๋ฉฐ ๊ฐ์ธ์ ์ผ๋ก ์ ๋ฆฌํ ๊ธ์
๋๋ค.
์ด๋ฏธ์ง์ ๋ํ ์ถ์ฒ๋ ๋ชจ๋ ์๋์ ์๋ ํฌ์คํ
์ ์์ต๋๋ค.