gpt4 book ai didi

inheritance - Groovy在这里做什么?

转载 作者:行者123 更新时间:2023-12-04 04:31:43 25 4
gpt4 key购买 nike

我正在尝试调试一些使用mixins的代码,并且能够将问题减少到此示例。我有一个通过mixin接收方法的父类,以及一个从父类继承的子类。如果我尝试在子类的实例上替换方法,则该方法可以正常工作,除非要替换的方法是在父类的实例上被调用之前被替换的。如果它已被调用,那么我将无法替换
所以这段代码:

class M {
protected foo() { println 'foo' }
}

@Mixin(M) class A {
def bar() { foo() }
}

class B extends A {}

def b = new B()
def a = new A()
a.bar() //<-- comment out this line and see the difference
b.metaClass.foo = {println 'winning'}
b.bar()
将产生:

foo

foo


但是,如果您注释掉第13行(带有注释的注释行),您将得到:

winning


为什么会这样?我希望在Groovy的元类模型的上下文中有某种有意义的方法,但是我不明白。
这是Groovy 1.8.6

最佳答案

metaClass是在方法调用上查看的,mixin有其自己的处理程序。
两者都是延迟加载和静态加载,如果不调用方法,则不会发生静态延迟加载。
Mixins优先于metaClass覆盖,这就是为什么在初始化A时显示foo而不赢的原因。
为了在每个类上解析元,都需要在对象上定义一个元,您需要Object.class.metaClass(即B.metaClass)。
有趣的是,这产生了:

groovy.lang.MissingMethodException: No signature of method: B.foo() is applicable for argument types: () values: []
Possible solutions: foo(), foo(java.lang.Object), bar(), any(), use([Ljava.lang.Object;), find(groovy.lang.Closure)

在B上定义foo可解决以下错误:
class B extends A {
def foo() { println 'not winning' }
}

您的答案是Mixin影响类元存储库,并且类方法优先于对象元存储库方法。

证明 :
@Mixin(M)
class B extends A {

}

a.bar() //<-- comment out this line and see the difference
B.metaClass.foo = {println 'class winning'}
b.metaClass.foo = {println 'object winning'}
b.bar()

产量:
foo
class winning

一种不同的方法
class M {
protected foo() { println 'foo' }
}

@Mixin(M) class A {
def bar() { foo() }
}

class B extends A {
def bar() { foo() }
}

class C extends B {
def foo() { println 'wat' }
}

@Mixin(M)
class D extends C { }

def b = new B()
def a = new A()
def c = new C()
def d = new D()


a.bar() //<-- comment out this line and see the difference
b.metaClass.foo = {println 'winning'}
b.bar()

c.metaClass.foo = {println 'losing'}
c.bar()

d.metaClass.foo = {println 'draw'}
d.bar()

产量
foo
winning
wat
wat

关于inheritance - Groovy在这里做什么?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9525376/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com