2010-01-31 2 views
12

Можно ли проверить класс, чтобы узнать, есть ли у него метод или нет? Или даже конкретное свойствоПроверьте, есть ли у класса метод

+0

хорошо выглядит, если я просто выполняю оператор if, который проверяет, работает ли свойство. но как насчет методов – numerical25

+0

Связанный: [Actioncript (flex): как узнать, существует ли (или определено) свойство объекта?] (http://stackoverflow.com/questions/1520610) –

ответ

29
var target:Object;// = some object 
var name:String;// = some name 
if(name in target){ 
    // if property/method exists 
}else{ 
    // if property/method not exists 
} 
+7

+1 Обратите внимание, что это не будет перечислять частные/защищенные свойства/функции объекта. – Amarghosh

+1

да, я, вероятно, не буду нуждаться в нем, если его частные или защищенные. спасибо – numerical25

+0

Это единственный правильный ответ относительно того, действительно ли свойство/метод существует (т. е. он перечислим), потому что свойство действительно может быть определено, несмотря на то, что значение «неопределено» даже при строгом равенстве. Например: 'var obj: Object = {a: undefined};' будет трассировать true для 'obj [" a "] === undefined', но свойство" a "все еще определено, о чем свидетельствует следующая трассировка цикла «a»: 'for (var key: * in obj) trace (key); // трассирует "a". Чтобы избавиться от свойства, вам нужно будет вызвать 'delete obj [" a "]'. Чтобы строго смотреть на ненулевую функцию, 'if (target [name] is Function) будет лучше. – Triynko

2
import flash.utils.describeType; 
... 
function methodExists(obj:Object,name:String):Boolean 
{ 
     var desc:XML=flash.utils.describeType(obj); 
     return (desc.method.(@name==name).length()>0); 
} 

(Примечание: сделано с верхней части моей головы)

+0

'describeType' не отображает динамические свойства , Попробуйте на этом объекте, например: «var target: Object = {a: 123, b:« ASD », c: function(): void {trace (" hello ");}}' - выводит описание простой объект с просто 'hasOwnProperty',' isPrototypeOf' и 'propertyIsEnumerable'. – Amarghosh

+0

Не нужно использовать 'describeType', который очень медленный. – miguelSantirso

+1

describeType может быть медленным, но если вы создадите метод для обработки XML в объектно-ориентированную структуру и кешируете его в словаре по имени типа, вы будете нести накладные расходы на descriptionType только при первом запуске для любого заданного типа , после чего простой поиск в словаре по имени типа очень быстрый (getQualifiedClassName (экземпляр или класс) примерно в 3000 раз быстрее). Единственный улов describeType - это не захватывает динамические свойства, но это по дизайну. – Triynko

2

Вы также можете вызвать методы/свойства от метода массива/поиска, например следующим образом. Если он не существует, он будет «неопределенным», который также считается «ложным».

var target:Object;// = some object 

if(target["propertyName"]){ 
    // if property/method exists 
}else{ 
    // if property/method not exists 
} 
+1

Возможно, лучше проверить на неопределенное значение 'if (target [" propertyName "] == undefined)'. В противном случае, если свойство определено, но установлено значение, которое оценивается как 'false' (т. Е. Строка emtpy,' null', '0' или' false'), это будет считаться «не существует». – IQAndreas

+0

Если я попытаюсь использовать это в функции, он будет разбиваться на меня с ошибкой 1069 - даже когда вы просто проверяете, истинно это или ложно. Я делаю это с ключевым словом this (для синтаксических исследований). Зачем? – Panzercrisis

+1

Вы должны использовать строгое равенство (===) для сравнения 'undefined'. Кроме того, только неопределенные переменные 'var x: *' могут хранить значение undefined. Null is (==) до неопределенного, но не (===) до неопределенного, поэтому, если свойство существует и имеет значение null, то по сравнению с undefined with == вернет true, несмотря на существующее свойство и значение null. Фактически даже при строгом равенстве свойство может быть * определено * и содержать значение «undefined», которое по-прежнему не совпадает с * будучи * undefined (т. Е. Выполняется цикл for (var key: * in obj) вернуть свойство). Поэтому верно только «if (key in obj)». – Triynko