JavaScript: `this`가 이렇게 작동하는 이유는 무엇입니까?
9981 단어 oopwebdevjavascript
this
키워드에 대해 생각하는 것입니다. 그들 중 많은 사람들에게 this
는 확실히 더 복잡한 앱에서 가장 문제를 일으켰습니다.다른 컨텍스트에서 키워드의 의미에 대한 많은 기사가 있지만 지금은
this
작동 방식을 설명하여 더 잘 이해할 수 있도록 하고 싶습니다.우선 자바스크립트 객체 시스템이 프로토타입을 기반으로 한다는 것을 기억하자. 프로토타입이란 무엇입니까? 실제로는 다른 개체에 의해 "상속"될 수 있는 개체일 뿐입니다. 프로토타입은 단순한 객체이므로 프로토타입 자체를 가질 수 있습니다.
주어진 개체의 속성이나 메서드에 액세스하려고 하면 먼저 개체 자체의 속성을 검색합니다. 찾을 수 없으면 개체의 프로토타입을 검색합니다. 그래도 찾을 수 없으면 프로토타입의 프로토타입을 검색합니다. 그런 다음 속성을 찾을 때까지 계속 검색합니다. 어디에서도 속성을 찾을 수 없으면
undefined
입니다.예를 들어 보겠습니다.
function DogThatQuacks(name) {
this.name = name
}
DogThatQuacks.prototype.bark = function() {
return `${this.name} says "Quack!"`
}
const bartholomew = new DogThatQuacks('Bartholomew')
// Outputs 'Bartholomew says "Quack!"'
bartholomew.bark()
마지막 줄에서 JavaScript 엔진은 먼저 개체
bartholomew
에 bark
메서드가 있는지 검색합니다. name
가 유일한 속성이므로 프로토타입을 조사합니다. 그곳에서 메소드를 찾고 마지막으로 DogThatQuacks.prototype.bark
를 실행합니다.문제는 메서드
bark
가 DogThatQuacks.prototype
가 아니라 객체bartholomew
에 있다는 것입니다. 메소드는 어떻게 접근할 수 있습니까bartholomew.name
? this
의 값은 함수를 호출하는 방법에 따라 다르기 때문입니다.결국 메서드
DogThatQuacks.prototype.bark
를 호출하지만 개체bartholomew
의 메서드로 호출합니다. 그런 이유로 이 경우 this
는 bartholomew
를 참조합니다. 이제 조금 더 플레이해 보겠습니다.// Outputs 'undefined says "Quack!"'
DogThatQuacks.prototype.bark()
// Outputs 'undefined says "Quack!"', but
// it throws an error in strict mode
const bark = bartholomew.bark
bark()
첫 번째 예에서는
DogThatQuacks.prototype.bark
를 직접 호출합니다! 짐작할 수 있듯이 this
는 name
속성이 없는 프로토타입 자체에 대한 참조입니다.그리고 두 번째 경우에는 엄격 모드를 사용하는 경우 오류가 발생하고 "undefined가 Quack을 말합니다!"엄격 모드가 아닌 경우. 왜요?
bark
를 객체의 메소드로 호출하지 않기 때문에 간단한 함수로 호출하는 것입니다.엄격 모드에서 함수를 호출할 때
this
가 정의되지 않습니다. 그리고 엄격 모드가 활성화되어 있지 않으면 전역 개체를 참조합니다. 다시 말하지만 this
값은 함수를 호출하는 방법에 따라 다릅니다.더 많은 예:
function makeDogBark(barkMethod) {
console.log(barkMethod())
}
// Outputs 'undefined says "Quack!"', but
// it throws an error in strict mode
makeDogBark(bartholomew.bark)
DogThatQuacks.prototype.actuallyBark = function() {
const internalFunction = function() {
return `${this.name} now says "Woof!"`
}
return internalFunction()
}
// Outputs 'undefined now says "Woof!"', but
// it throws an error in strict mode
bartholomew.actuallyBark()
첫 번째 예에서는
bartholomew.bark
를 함수 makeDogBark
에 인수로 전달합니다. 그러나 함수는 인수barkMethod
, 즉 단순 함수를 호출합니다.두 번째 경우에는 다시 단순 함수
internalFunction
를 호출하므로 엄격 모드가 활성화되었는지 여부에 따라 정의되지 않거나 전역 객체입니다.또한 모든 것이 수업에도 적용된다는 점을 고려해야 합니다. 이것이 JavaScript의 클래스가 프로토타입을 위한 구문 설탕인 이유입니다.
class CatThatSaysMoo {
constructor(name) {
this.name = name
}
meow() {
return `${this.name} says "Moo!"`
}
}
const florence = new CatThatSaysMoo('Florence')
// Outputs 'Florence says "Moo!"'
florence.meow()
// Outputs 'undefined says "Moo!"'
CatThatSaysMoo.prototype.meow()
const meowFunction = florence.meow
// Throws an error, `this` is undefined
meowFunction()
메서드를 함수에 인수로 전달해야 하거나 변수에 메서드를 저장해야 하는 경우 화살표 함수(부모 범위에서
this
를 "상속") 또는 bind
방법:DogThatQuacks.prototype.actuallyBark = function() {
const internalFunction = () => {
// It inherits the `this` from
// `DogThatQuacks.prototype.actuallyBark`
return `${this.name} now says "Woof!"`
}
return internalFunction()
}
// Outputs 'Bartholomew now says "Woof!"'
bartholomew.actuallyBark()
// If fixes `this` as a reference
// to the object `florence`
const meowFunction = florence.meow.bind(florence)
// Outputs 'Florence says "Moo!"'
meowFunction()
추신. 읽은 내용이 마음에 드셨나요? 매주 저는 더 나은 JavaScript 개발자가 되기 위한 무료 팁과 통찰력이 포함된 이메일을 보냅니다. 관심이 있으시면 click here to subscribe .
Reference
이 문제에 관하여(JavaScript: `this`가 이렇게 작동하는 이유는 무엇입니까?), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://dev.to/nicozerpa/javascript-why-does-this-work-like-this-478i텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)