2017-12-09 23 views
0

업데이트 : @Bergi의 게시가 this thread 인 경우 상위 생성자를 호출하는 대신 Reflect.construct을 사용해야한다고 설명합니다. 이것은 질문을 "Constructor.call()과 Reflect.construct()"의 기술적 차이점으로 이동시킵니다. 모든 의견에 감사드립니다.

javascript가 어떻게 작동합니까?

꽤 오래 동안 새로운 프로토 타입 프로토 타입을 확장하여 모든 유형을 확장했습니다. 예 :

const B = function(){ 
    return A.call(this); 
}; 

B.prototype = Object.create(A.prototype); 

B.prototype.extra_method = function(){ 
    console.log('hello'); 
} 

최근에 나는이 방법은 ES6 class extends로 할 수없는 것을 tho를 발견했습니다 : I 클래스 "사람"을 확장하고 싶었다면 내가 좋아하는 뭔가를 NewType.prototype=Object.create(Person.prototype);를 호출하여 내 확장 프로토 타입을 만들 것입니다. 예를 들어, 내장형을 확장하고 싶다면 class extends 키워드 만 사용하면됩니다. 왜 그런가요?

예 A이 (작동하지 않습니다) :

const ArrayExt = function(){ 
    this.extra_variable = 'hello!'; 
    return Array.call(this,...arguments); 
} 

ArrayExt.prototype = Object.create(Array.prototype); 

ArrayExt.prototype.extra_method = function(){ 
    console.log('Method called!'); 
} 

var inst = new ArrayExt(1,2,3); 

inst.push(4); 
inst.length == 4 //seems to work right? 

inst.extra_method == undefined //not included 
inst.extra_variable == undefined //not included (why?) 


예 B (작품) :

생성자 사이의 기술적 차이는 무엇
const ArrayExt = class extends Array{ 
    constructor(){ 
     super(...arguments); 
     this.extra_variable = 'Hello!'; 
    } 

    extra_method(){ 
     console.log('I actually am here now!'); 
    } 
}; 

var inst = new ArrayExt(1,2,3); 

inst.push(4); 
inst.length == 4 //works 
inst.extra_variable == 'Hello!' //works 
inst.extra_method() //'I actually am here now!' works 
+1

클래스 및 확장은 구식 "클래스"및 "확장"에 대한 구문 식 설탕입니다. 변환기를 사용하여 ES6을 이전 구문으로 변환하면 이것이 다소 정확하다는 것을 확인할 수 있습니다. – apokryfos

+0

그러면 확장 키워드로 만 내장 유형 (배열, 함수)을 확장 할 수 있습니까? –

+2

https://stackoverflow.com/questions/33369131/is-it-possible-to-inherit-old-style-class-from-ecmascript-6-class-in-javascript가 적합 해 보입니다. 또한 귀하의 질문에 귀하의 의견을 말하고 반대를 요구하고 있습니다. – apokryfos

답변

1

. call() 및 Reflect.construct()

함수 개체의 용도가 다릅니다. Example()new Example()의 차이와 같습니다.

두 표현식은 항상 객체가 가질 수있는 두 가지 다른 내부 메서드 ([[call]][[construct]])로 해결하여 각각 다른 작업을 수행했습니다. ES6에서는 단지 하나만 작동하는 새로운 유형의 기능을 도입했습니다 (화살표, 메소드 : 호출, class 생성자 : 구조). function 구문에서 작성된 함수는 항상 바람직하지 않은 경우에도 둘 다 사용 가능하게했습니다.

+0

@ Bergi에게 감사드립니다. new 연산자는 myType.call (Object.create (myType.prototype))에서와 같이 새로운 인스턴스로 생성자 함수를 호출한다고 가정했습니다. new 연산자가 this [[construct]] 메서드를 호출하는 대신에 그렇게하지 않는 특별한 이유가 있습니까? –

+1

@JohnSmith 정확하지는 않습니다. 'new'는 이전의'function' 생성자로이 인스턴스 생성과 함수 본문 실행 (반환 값에 대한 몇 가지 사항)을 수행하는 [[construct]] 메소드를 호출합니다. 'Date' 나'HTMLElement'와 같은 몇몇 내장 함수들은 전체적으로 다르게 작동했습니다. 이제는 ES6에서 확장 성이 있습니다. – Bergi

+0

이렇게하면 문제가 해결됩니다. 정보 주셔서 감사합니다! –