开发者

Method overloading in groovy

I am trying to take advantage of the convenience of groovy's scripting syntax to assign properties, but having trouble with a specific case. I must be missing something simple here. I define class A, B, C as so:

class A {

    A() {
        println "Constructed class A!"
    }

}

class B {

    B() {
        println "Constructed class B!"
    }

}

class C {

    private member 

    C() {
        println "Constructed class C!"
    }

    def setMember(A a) {

        println "Called setMember(A)!"
        member = a

    }

    def setMember(B b) {

        println "Called setMember(B)!"
        member = b

    }

}

And then try the following calls in a script:

开发者_Python百科
c = new C()

c.setMember(new A()) // works
c.member = new A()   // works

c.setMember(new B()) // works
c.member = new B()   // doesn't work!

The last assignment results in an error: 'Cannot cast object of class B to class A". Why doesn't it call the proper setMember method for class B like it does for class A?


The shortcut of using the dot notation for calling a property's setter method doesn't do type checking. Instead it seems to use the first entry in the list of methods with a given name and invoke it.

You can also read Pyrasun's extended comments on the shortcomings of Groovy's property handling.

If you want to bypass this (mis)behavior you have to call the setter directly, as Groovy supports type checking for method calls. Alternatively you could also access the field directly without a setter using

c.@member = new B()

or you do the type checking on your own in a single setter method:

def setMember(def param) {
  if (param instanceof A) println "Called setMember(A)!"
  if (param instanceof B) println "Called setMember(B)!"

  member = param
}
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜