2009-10-07 42 views
35

Giả sử rằng tôi có một đối tượng someObj loại không xác định, tôi muốn làm một cái gì đó như:Trong groovy, có cách nào để kiểm tra xem một đối tượng có một phương thức nhất định không?

def value = someObj.someMethod() 

đâu có gì bảo đảm rằng 'someObj' thực hiện các phương pháp someMethod(), và nếu không, chỉ trả lại null.

Có điều gì giống như vậy trong Groovy không, hoặc tôi có cần bọc nó trong câu lệnh if với séc instanceof không?

+0

Một cách sẽ được interate '.properties' mỗi http://stackoverflow.com/questions/2585992/how-to-get-all -property-name-of-a-groovy-class – MarkHu

Trả lời

57

Sử dụng respondsTo

class Foo { 
    String prop 
    def bar() { "bar" } 
    def bar(String name) { "bar $name" } 
} 

def f = new Foo() 

// Does f have a no-arg bar method 
if (f.metaClass.respondsTo(f, "bar")) { 
    // do stuff 
} 
// Does f have a bar method that takes a String param 
if (f.metaClass.respondsTo(f, "bar", String)) { 
    // do stuff 
} 
4

Bạn sẽ có thể làm điều gì đó như:

SomeObj.metaClass.getMetaMethod("someMethod") 

Hoặc bạn có thể rơi trở lại cái cũ phản ánh Java API tốt.

+2

Không có gì tốt về API relection :) –

3

Chỉ cần thực hiện methodMissing trong lớp học của bạn:

class Foo { 
    def methodMissing(String name, args) { return null; } 
} 

Và sau đó, mỗi khi bạn cố gắng để gọi một phương pháp mà không tồn tại, bạn sẽ nhận được một giá trị null.

def foo = new Foo(); 
assert foo.someMethod(), null 

Để biết thêm thông tin, hãy xem ở đây: http://groovy.codehaus.org/Using+methodMissing+and+propertyMissing

+0

Điều đó có nghĩa là tất cả các đối tượng của mình mà không có hành vi someMethod sẽ phải thực hiện phương pháp? – Langali

2

Bạn có thể đạt được điều này bằng cách sử dụng getMetaMethod cùng với các nhà điều hành chuyển hướng an toàn ?.:

def str = "foo" 
def num = 42 

def methodName = "length" 
def args = [] as Object[] 

assert 3 == str.metaClass.getMetaMethod(methodName, args)?.invoke(str, args); 
assert null == num.metaClass.getMetaMethod(methodName, args)?.invoke(num, args); 
2

nếu lớp:

MyClass.metaClass.methods*.name.any{it=='myMethod'}//true if exist 

nếu đối tượng:

myObj.class.metaClass.methods*.name.any{it=='myMethod'}//true if exist 
Các vấn đề liên quan