Groovy 获取子类型的元类

Groovy get metaClass of subtype

我尝试将属性动态添加到继承自一个常见类型 class 的类型的实例。为了让用户更简单,我想在 super class:

中创建一个辅助方法
class Super {
    void add(String propertyName, Object value) {
        this.metaClass."$propertyName" = value
    }
}

class X extends Super {
    String name
    int value
}

X a = new X(name: 'a', value: 4)
X b = new X(name: 'b', value: 5)

a.add('other', 5)
b.add('other', 4)

println a​​.other
println b.other​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​

此代码打印:

4
4

但是,如果使用 "add" 方法,我直接在实例上设置元属性:

a.metaClass.other = 5
b.metaClass.other = 4

println a​​.other
println b.other​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​​

它打印:

5
4

我知道不只有一个元class 例如,每个层级class 都有自己的层级。有没有办法获得 subclass 的 metaclass 或者我完全错过了这个想法?

更新

如果我在 subclass 中添加:

    {
        super.setMetaClass(metaClass)
    }

它似乎有效,但我宁愿避免它。

我看到子类型元类看起来像:

org.codehaus.groovy.runtime.HandleMetaClass@25b53784[groovy.lang.ExpandoMetaClass@25b53784[class X]]

和超类型元类:

groovy.lang.ExpandoMetaClass@25b53784[class X]

如果您想使用父级的 class metaClass,您需要使用 super.metaClass 而不是 this.metaClass 来访问它,如下例所示:

class Super {
    void add(String propertyName, Object value) {
        super.metaClass."$propertyName" = value
    }
}

class X extends Super {
    String name
    int value
}

X a = new X(name: 'a', value: 4)
X b = new X(name: 'b', value: 5)

a.add('other', 5)
b.add('other', 4)

println a.other
println b.other

输出:

$ groovy test.groovy
5
4

或者,您可以使用与 this.metaClass 配合良好的特征(特征将 add 方法添加到实现特征的 classes,因此 this.metaClass 可以作为预期在这种情况下。)

trait Super {
    void add(String propertyName, Object value) {
        this.metaClass."$propertyName" = value
    }
}

class X implements Super {
    String name
    int value
}

X a = new X(name: 'a', value: 4)
X b = new X(name: 'b', value: 5)

a.add('other', 5)
b.add('other', 4)

println a.other
println b.other