2011-04-10 3 views
4

클래스 정의가 상속을 통해 제공되는지 또는 특정 메소드를 제공 하는지를 확인해야합니다. 이 작업을 수행하려면 프로토 타입 체인을 사용해야합니까?메소드가 JavaScript 클래스에 정의되어 있는지 확인하려면 어떻게해야합니까?

function TestClass(config){ 
    //NOTE: cannot instantiate class because if config not valid Error is thrown 
} 
TestClass.prototype.sampleMethod = function(){}; 

function isDefined(klass){ 
     console.log(typeof klass.sampleMethod); //'undefined' 
     console.log('sampleMethod' in klass); //false 
     console.log(klass['sampleMethod']); //undefined 

     console.log(typeof klass.prototype.sampleMethod); //'function' ...inheritance? 
} 

isDefined(TestClass); 

답변

0

예, 프로토 타입 체인을 확인해야합니다.

function TestClass(config){} 
TestClass.prototype.sampleMethod = function(){}; 

function TestClass2() {} 
TestClass2.prototype = TestClass; 

function isDefined(obj, method) { 
    if (obj.prototype !== undefined) { 
     var methodInPrototype = (method in obj.prototype); 
     console.log("Is " + method + " in prototype of " + obj + ": " + methodInPrototype); 
     if (methodInPrototype) { 
       return true; 
     } else { 
      isDefined(obj.prototype, method); 
     } 
    } 
    return false; 
} 

isDefined(TestClass, "sampleMethod"); 
isDefined(TestClass2, "sampleMethod"); 
isDefined(TestClass2, "sampleMethod2"); 

인쇄가 : 당신이 생성자를 테스트하는 것 왜

// Is sampleMethod in prototype of function TestClass(config) {}: true 
// Is sampleMethod in prototype of function TestClass2() {}: false 
// Is sampleMethod in prototype of function TestClass(config) {}: true 
// Is sampleMethod2 in prototype of function TestClass2() {}: false 
// Is sampleMethod2 in prototype of function TestClass(config) {}: false 
+0

또한 메서드가 진정한 함수인지 ala (typeof 메서드 === 'function')가 아닌 진정한 함수인지 확인하는 것이 좋습니다. – sonicwizard

0

이게 무슨 일입니까? 이것이 무엇의

function TestClass(config) {} 
TestClass.prototype.sampleMethod = function() {}; 

function isDefined(klass, method) { 
    return (klass && method ? 
    function() { 
     return !!klass.prototype[method]; 
    }() : false); 
} 

예 : 나는 문제가 클래스 뭔가를 구현하는 경우 특별히의 인스턴스를 할당하지 않는 한, 직접 클래스의 인스턴스를 보지 않고 감지 할 수있을 것 같아요 http://fiddle.jshell.net/Shaz/2kL9A/

+0

일종의 경우 상속 여부를 감지하지 못합니다. function TestClass2() {} TestClass2.prototype = TestClass; isDefined (TestClass2, 'sampleMethod') 프로토 타입 체인을 걷는 코드를 실행하는 바로 가기가 있는지 궁금합니다. – Ivo

+0

모두 참조 할 수 없으므로 안정적으로 "프로토 타입 체인을 걷지"못합니다. 그것 [[프로토 타입]] 개체. 인스턴스를 만들고 메소드가 있는지 확인하십시오. – RobG

+0

왜 프로토 타입 체인을 sonicwizard 예제처럼 탐색 할 수 없습니까? – Ivo

1

그것은 검사를위한 새로운 클래스의 프로토 타입입니다. 클래스의 프로토 타입에 속성 sampleMethod가 주어지면 클래스가 아닌 프로토 타입을 나타내는 인스턴스 객체라는 것을 기억하십시오. 사실, 클래스는 자바 스크립트에서 실제로 그렇게 존재하지 않습니다.

function TestClass(config){} 
TestClass.prototype.sampleMethod = function(){}; 

function isDefined(klass){ 
    var holder, _defined = false; 
    try{ 
    holder = new klass({}); 
    _defined = typeof holder.sampleMethod !== 'undefined'; // does the prototype lookup for you 
    }catch(e){ 
    console.log('Error loading class for reasons other than invalid method.', e) 
    }finally{ 
    return _defined; 
    } 
} 
0

내가 볼 수없는, 난 그냥 특별한 방법을 가지고 있는지 확인하기 위해 직접 객체를 테스트하는 것입니다. [[프로토 타입]], 다른 뭔가가 필요 통해 고전적인 프로토 타입 상속에만 적합 물론 위의

function MyConstructor(){} 
MyConstructor.prototype.sampleMethod = function(){}; 

// Return true if instances of constructor have method 
// Return false if they don't 
// Return undefined if new constructor() fails 
function isDefined(constructor, method){ 
    var temp, defined; 
    try { 
    temp = new constructor(); 
    defined = !!(typeof temp[method] == 'function'); 
    } catch(e) { 
    // calling - new constructor - failed 
    } 
    return defined; 
} 

var foo; 

alert(
    isDefined(MyConstructor, 'sampleMethod')    // Method on MyConstructor.prototype 
    + '\n' + isDefined(MyConstructor, 'undefinedMethod') // Not defined 
    + '\n' + isDefined(MyConstructor, 'toString')  // Method on Object.prototype 
    + '\n' + isDefined(foo, 'foo')      // foo is not a constructor 
); 

:

어쨌든, 가브리엘은 아주 가까이,하지만 난 다르게 조금 할 줄 모듈 패턴 또는 유사 물이 사용되는 곳 (즉 클로저를 사용하는 "inhertiance").

+0

생성자가 매개 변수를 사용하고 잘못된 입력에 예외를 throw 할 수 있습니다. – Ivo

관련 문제