简体   繁体   English

Groovy 闭包可以扩展抽象 class

[英]Can a Groovy closure extend an abstract class

I have an abstract Java class that needs to have one method onMessage to be implemented.我有一个抽象的 Java class 需要有一个方法onMessage来实现。 I know that a closure can easily implement a Java interface using the as keyword, but how can it extend an abstract Java class?我知道闭包可以使用as关键字轻松实现 Java 接口,但它如何扩展抽象 Java class?

If it can't extend it, then whats the best work around possible in such cases in Groovy?如果它不能扩展它,那么在 Groovy 的这种情况下,最好的解决方法是什么?

Here is my usage in Java, I am looking for something similar that can be done in Groovy.这是我在 Java 中的用法,我正在寻找可以在 Groovy 中完成的类似操作。

MessageCallback callback = new MessageCallback() {
            @Override
            public void onMessage(Message message) {
                dosomething();
            }
        };

Where message callback is my abstract class which I would like to use in a similar fashion in Groovy.其中消息回调是我的抽象 class,我想在 Groovy 中以类似的方式使用它。

I believe you should be able to do:我相信你应该能够做到:

def callback = [ onMessage:{ message -> doSomething() } ] as MessageCallback

Does that not work?那不行吗?

Edit编辑

To make a call from the Map method back to the Abstract class, the only way I can find to do it is:要从 Map 方法调用抽象 class,我能找到的唯一方法是:

// Dummy class for testing
abstract class MessageTest {
  abstract void onMessage( msg ) ;
  void done() { println "DONE!" }
}

// Create a Proxied instance of our class, with an empty onMessage method
def p = [ onMessage:{ msg -> } ] as MessageTest

// Then overwrite the method once we have access to the Proxy object p
p.metaClass.onMessage = { msg -> println msg ; p.done() }

// Test
p.onMessage( 'woo' )

Yo can do this:哟可以这样做:

Implements a method in any class:在任何 class 中实现一个方法:

public MessageTest messageTest(Closure callback) {
    return new MessageTest() {
        @Override
        public void onMessage(Message message) {
            callback.call(message)
        }
    }
}

In main class in main method:在主要方法中的主要 class 中:

def outerMessage

MessageTest messageTest = messageTest() {message ->
    outerMessage = message
    println "innerMessage: $message"
}

messageTest.onMessage("This is the message...")
println "outerMessage: $outerMessage"

Your output should show this:您的 output 应该显示:

innerMessage: This is the message...
outerMessage: This is the message...

Basing on @tim_yates, here is a version of method which creates object of an abstract class from a closure.基于@tim_yates,这是一个从闭包创建抽象 class 的 object 的方法版本。 I needed something like that to be able instantiate such object in just one line.我需要这样的东西才能在一行中实例化这样的 object。

// Dummy class for testing
abstract class MessageTest {
  abstract void onMessage( msg ) ;
  void done() { println "DONE!" }
}

MessageTest createMessageTest(Closure closure) {
  // Create a Proxied instance of our class, with an empty onMessage method
  def p = [ onMessage:{ msg -> } ] as MessageTest

  // Then overwrite the method once we have access to the Proxy object p
  p.metaClass.onMessage = closure
  return p
}

// Create
MessageTest mt = createMessageTest { msg -> 
  println msg ; 
  done() 
}

// Test
mt.onMessage( 'woo' )

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM