Java 8:使用静态方法而不是静态util类接口

时间:2014-08-02 20:07:38

标签: java static java-8

当我需要一堆无状态实用程序方法时,Java 8中的最佳实践是什么。拥有一个的界面是正确的,即public interface Signaturespublic interface Environments,或者以旧的方式做得更好 - 拥有{{1} }和public final class Signatures私有构造函数||枚举?

5 个答案:

答案 0 :(得分:28)

接口的主要目的是提供该类型的操作(方法)的类型和词汇表。它们是有用且灵活的,因为它们允许多个实现,实际上它们被设计为允许在类层次结构中不相关的实现。

问题是,

  

拥有一个不会被任何人实现的界面是对的吗??

在我看来,这样可以减少对接口的影响。人们必须环顾API以确定没有实现此接口的类,并且没有此接口的生产者或使用者。有人可能会感到困惑,并试图创建一个接口的实现,但当然他们不会走得太远。虽然可以使用所有静态方法的“实用程序接口”,但这并不像旧的不可构造的最终类成语那样清晰。后者的优点是类可以强制执行,不会创建任何实例。

如果你看一下新的Java 8 API,你会看到尽管能够在接口上添加静态方法,仍然会使用最终的类习惯用法。

接口上的静态方法已用于诸如工厂方法之类的东西,以创建这些接口的实例,或者用于在这些接口的所有实例中具有普遍适用性的实用程序方法。例如,请参阅Stream中的Collectorjava.util.stream接口。每个都有静态工厂:Stream.of()Stream.empty()Collector.of()

但请注意,每个都有伴随工具类StreamSupportCollectors。这些是纯实用程序类,仅包含静态方法。可以说它们可以合并到相应的接口中,但这会使接口混乱,并且会模糊类中包含的方法的关系。例如,StreamSupport包含一系列相关的静态方法,这些方法都是SpliteratorStream之间的所有适配器。将这些合并到Stream可能会让事情变得混乱。

答案 1 :(得分:6)

我会使用最后一堂课。更好地告诉我它是一个带有一些实用方法的辅助类。接口定义是我期望实现的东西,以及帮助某人实现接口的方法。

答案 2 :(得分:2)

接口中的静态方法添加了两个主要目的:

  1. 如果子类中实现不良,可以使用静态接口方法提供检查(例如,如果值为null)。

  2. 避免使用通用实用程序类(如Collections)并通过适当的接口调用静态方法。

  3. 因此,如果您打算与相应的类共享功能,那么这是一个非常好的做法。

    更新:

    如果您希望构建纯函数集合,那么您可能希望将抽象类与静态方法和私有构造函数一起使用。

答案 3 :(得分:2)

在良好的面向对象设计中,没有很多(如果有的话)无状态实用方法。

我要处理的最好的技巧是使用状态(对象)来处理函数。

所以不要做

 Temperature.farenheitFromCelcius(...);

我做

 public class FarenheitFromCelcius implements Function<Celcius, Farenheit> {

    public Farenheit apply(Celcius celcius) {
      return new Farenheit(5 * celcius.getValue() / 9 + 32);
    }

 }

这有一些优点。一个是它可以更容易地从内存中卸载。另一个是你可以节省类型识别接口的数量,你可以在方法之间传递实用程序方法,最后可以利用Java类型层次结构。

成本极低。基本上你必须改变方法的应用方式。

 public <T> R convertTemp(T temp, Function<T, R> conversion) {
   return conversion.apply(temp);
 }

当然,你永远不会编写一个完整的方法来封装面向对象的函数,但我必须展示一个例子...

答案 4 :(得分:0)

在您的情况下,我会上最后一堂课,而不是因为某人可能会实施或固有的this而感到疲劳。对于需要静态util接口的用例。我想我们需要一个最终接口...

public final class Util {

      private Util {
          throw new AssertionError("Please don't invoke me");
       }

    public static someUtilMethod() {}

    private static someHelperUtilMethod() {}

    }