如何在Java中优雅地包装重载方法?

时间:2018-07-29 14:04:51

标签: java generics overloading

例如,有一些重载的方法setData(T data),其中T可以是Something.BuilderSomething(它们或{{1都没有实现通用接口) }}将不接受通用接口作为其参数。

以下代码将起作用,但引入重复的代码。

setData

还有更好的选择吗?

例如,我们可以将它们合并为C ++中的一个功能模板:

public void setSomething(Something.Builder data) {
    thirdPartyLib.setData(data);
    ...
    cache = null;
}

public void setSomething(Something data) {
    thirdPartyLib.setData(data);
    ...
    cache = null;
}

但是我们如何在Java中做到呢?

2 个答案:

答案 0 :(得分:1)

如果我理解正确,thirdPartyLib.setData(data)有(至少)两个重载版本,一个为Something,一个为Something.Builder

在Java中,重载的方法彼此完全不同,只是碰巧具有相同的名称。如果一个被称为setSomethingData(Something data),另一个被称为setSomethingBuilderData(Something.Builder data),您将获得完全相同的行为。您无法写下在运行时在两个版本之间切换的单个调用。

因此至少对于setData()调用,您的代码需要有两个单独的语句。然后我看到了三种方法:

  • 使用问题中给出的重复的setSomething()方法。如果这只是这两种方法的共同点,那没关系。
  • 有两个setSomething()方法,但是将公共部分重构为某种辅助方法。如果有更多的通用代码行,我会这样做。
  • 具有一个setSomething(Object data)方法,该方法使用setData()测试和强制转换在内部确定要调用哪个instanceof版本。我避免像瘟疫一样避免这种情况,因为它将类型检查从编译时移到运行时。

讨论完您的明确问题后,让我问您是否真的要传递构建器而不是“真实”对象。那不是建筑商通常的意图。

答案 1 :(得分:0)

在这种情况下,您可以使用泛型。 希望这会有所帮助


public <T> void setSomething(T data) {
    thirdPartyLib.setData(data);
        ...
        cache = null;

    }