带有抽象类的 RMI/事件监听器?
一般来说,我们在事件监听中也使用接口概念来实现 RMI,我们都使用接口。为什么我们不能在这两种情况下使用抽象类。
Generally we are using interface concept for RMI implementation also in Event listening ,we are using interfaces .Why cant we use abstract classes in both theses cases.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
因为 RMI 需要使用 JRE 的代理生成逻辑在运行时生成实现这些接口的存根和骨架类。这不适用于抽象类,因此所有 RMI 操作都必须定义为接口。
Because RMI needs to generate stub and skeleton classes at runtime which implement those interfaces, using the JRE's proxy generation logic. This doesn't work with abstract classes, so all RMI operations must be defined as interfaces.
对于事件:因为正常情况是我们有一个自己的实现类,它很可能需要监听几个不同的事件;我们不能扩展两个不同的抽象类。
Skaffman 已经解释了使用 RMI 抽象类的一个问题。我想更进一步,抽象类对于这个目的来说是完全错误的概念。服务提供商需要向其客户提供有关如何调用服务的信息。接口正是我们所需要的 - 它告诉客户端可以做什么,但不告诉客户端如何完成它。当我们给出一个抽象类时,我们包括(部分)实现信息。客户端不需要看到这一点,并且在 RMI 上下文中甚至可能无法编译它 - 服务器中的抽象类可能引用客户端甚至没有的类。当然,您可以删除客户不需要的所有内容,所有实现等,瞧!您回来时只得到了界面中所需的信息。
所以我的做法是:
定义我的接口,我与外界的契约。
如果我可能有该接口的多个实现,特别是如果我想帮助实现者,请定义一个实现该接口的抽象类。在该抽象类中包含公共实现代码,并留下一些抽象方法供实现者实际填写。
或者简单地说:为客户端提供接口,为实现者提供抽象类,您很可能选择使用两者。是的,这确实意味着一些重复,这就是我们拥有优秀 IDE 的原因。
For events: because the normal situation is that we have an implementation class of our own and it may well neeed to listen to several different events; we can't extend two different abstract classes.
Skaffman has already explained one issue with using abstract classes for RMI. I'd go a step further, an Abstract Class is just completely the wrong concept for this purpose. The service provider needs to give its clients information about how to call the service. An Interface is exactly what we need for that - it tells the client what can be done and nothing about how it is done. When we give an Abstract class we are including (partial) implementation information. The client has no need to see this, and in an RMI contect may not even be able to compile it - the Abstract Class in the server may refer to classes the client doesn't even have. Sure you could trim out all the stuff the client does not not need, all the implementation etc, and lo! You're back with just the information needed in an Interface.
So my practice:
Define my Interfaces, my contract with the outside world.
If I may have several implementations of that Interface, and especially if I want to help the implementor, define an Abstract Class which implements the Interface. Include the common implementation code in that Abstract Class, and leave some methods abstract for the implementor to actually fill in.
Or to put it simply: Interface for the clients, Abstract Classes for the implementors, and you may well choose to use both. And yes that does imply some duplication, and that's why we have nice IDEs.