能否方法重载自动区分接口实现?

huangapple go评论63阅读模式
英文:

Can method overloading discriminate automatically between an interface implementations?

问题

我有两个实现接口的类:

public interface Vehicle {}
public class Car implements Vehicle {}
public class Shoes implements Vehicle {}

在用户级别上,我正在处理接口,函数通常具有以下形式:function(Vehicle v)

public class Controller {

    @Inject
    Service service;

    public int get(Vehicle v) {
        return service.getShortestPathLength(v);
    }
}

然而,在某个时候,我希望能够区分这两个实现,因为在这个特定部分上的操作非常不同(例如,在我的示例中,步行、汽车、飞机或船的路径将完全不同)。也就是说,我希望 getShortestPathLength(v) 可以自动切换(即,无需显式的 if 测试)到正确的重载方法,具体取决于 v 的实现:

public class Service {

    public int getShortestPathLength(Car c) {}
    public int getShortestPathLength(Shoes s) {}

}

然而,它似乎不能正常工作,我收到了一个 未解析的编译问题 错误:

> 在类型 Service 中,方法 getShortestPathLength(Vehicle) 不适用于参数 (Car)

我试图实现的目标是否可能实现,如果是,我错过了什么?

我目前的解决方法是在 getShortestPathLength(Vehicle v) 中测试 v.getClass().getSimpleName(),虽然它可以工作,但似乎不是最优的面向对象编程的使用方式。

顺便提一下,我正在使用 Java 11 和 Quarkus 1.6.0。

英文:

I have two classes implementing an interface :

public interface Vehicle {…}
public class Car implements Vehicle {…}
public class Shoes implements Vehicle {…}

At the user level I am dealing with the interface, and functions are usually of the form function(Vehicle v) :

public class Controller {

    @Inject
    Service service;

    public int get(Vehicle v) {
        return service.getShortestPathLength(v);
    }
}

However at some point I have a method which I want to be able to discriminate between the implementations, because the operations on this particular part are very different (e.g. in my example sample the paths by foot, by car, by plane or by boat would be completely different). That is, I would like getShortestPathLength(v) to switch automatically (i.e. without explicit if testing) to the correct overloaded method depending on the implementation of v :

public class Service {

    public int getShortestPathLength(Car c) {…}
    public int getShortestPathLength(Shoes s) {…}

}

However it doesn’t seem to work as is, I get an Unresolved compilation problem error :

> The method getShortestPathLength(Vehicle) in the type Service is not applicable for the arguments (Car)

Is what I am trying to achieve possible, and if so what am I missing ?

My current workaround is to test v.getClass().getSimpleName() within getShortestPathLength(Vehicle v), but although it works it doesn’t seem quite an optimized use of object-oriented programming.

FWIW I’m running Java 11 with Quarkus 1.6.0.

答案1

得分: 1

我可以提供三个选项:

  • 将getShortestPathLength()移至Vehicle,并根据Car和Shoes的各自特性进行不同实现。此选项增强了封装性。如果此选项能够根据您的逻辑来实现,且getShortestPathLength可以使用Vehicle中的数据来实现,则不需要其他信息。
  • 在Service中使用重载技术声明三个不同的函数,并将Service实现的代码分割成小的有意义的块,以便在不同函数中重复使用它们。通过使用此选项,我们必须为每次调用提供正确类型的参数,以便加载正确的方法。
  • 在Service中声明一个带有一个方法getShortestPathLength的接口。使用不同的逻辑为Service实现不同的变体。正确地注入Service的实例,以便调用正确的实现。此选项基于Service的多态性。

您的解决方案也不错,但我认为在运行时检查实体类型不是一个好主意。

英文:

I can suggest three options:

  • Move getShortestPathLength() to Verhicle, and implement differently depends on individual charaters of Car and Shoes. This option increases encapsulation. If this option can be implemented depends on your logic. In case getShorttestPathLength can be implemented using data in Verhicle, no other information required
  • Declare 3 different functions using overloading technique in Service, and divide your code in Service implementation to small meaningful block to get them reused in different functions. By using this option, we have to give correct type of parameter for each call, in order to get correct method to be loaded.
  • Declare an interface of Service with one method: getShortesPathLength. Implement different variants for Service with different logic. Inject correctly instances of Service so that correct implementation can be called. This option based on polymorphism of Service

Your workaround is not bad, but I do not think checking type of entities in run time is good idea.

huangapple
  • 本文由 发表于 2020年8月17日 22:56:21
  • 转载请务必保留本文链接:https://go.coder-hub.com/63453420.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定