使用闭包映射在Groovy中实现接口时(如在http://groovy.codehaus.org/Groovy+way+to+implement+interfaces中)有没有办法在使用as关键字或asType方法实现接口后将对象转换回映射?
答案 0 :(得分:6)
根据您的用例,您似乎可以在将其转换为所需界面之前保留对原始Map
的引用。
但是,查看将Map
对象转换为接口的源代码(使用Proxy
),看起来您可以通过获取{{1来重新检索原始地图代表。
InvocationHandler
注意:这取决于Groovy代码的内部,因此使用风险由您自行承担:
答案 1 :(得分:2)
有趣的问题......简短的回答,没有。答案很长,也许......假设你有类似的东西:
def i = 1
Iterator iter = [ hasNext:{ true }, next:{ i++ } ] as Iterator
然后调用
println iter.take( 3 ).collect()
打印[1,2,3]
现在,您可以声明一个方法来执行此操作:
def mapFromInterface( Object o, Class... clz ) {
// Get a Set of all methods across the array of classes clz
Set methods = clz*.methods.flatten()
// Then, for each of these
methods.collectEntries {
// create a map entry with the name of the method as the key
// and a closure which invokes the method as a value
[ (it.name): { Object... args ->
o.metaClass.pickMethod( it.name, it.parameterTypes ).invoke( o, args )
} ]
}
}
这允许你这样做:
def map = mapFromInterface( iter, Iterator )
并致电:
println map.next()
println map.next()
将打印4
后跟5
使用println map
打印地图,提供:
[ remove:ConsoleScript43$_mapFromInterface_closure3_closure4@57752bea,
hasNext:ConsoleScript43$_mapFromInterface_closure3_closure4@4d963c81,
next:ConsoleScript43$_mapFromInterface_closure3_closure4@425e60f2 ]
但是,因为这是一个映射,任何包含多个具有相同名称和不同参数的方法的类都将失败。我也不确定在第一种情况下做这件事是多么明智......
您感兴趣的用例是什么?