BooleanSupplier使用场景

San*_*alp 5 java-8

我正在考虑使用时试图理解用例场景BooleanSupplier.在其解释中的大多数例子中,我得到的最多.我想了解使用BooleanSupplier提供的优势比简单的比较更有用吗?

    String s1 = "ABC";
    String s2 = "ABC";

    BooleanSupplier stringEquals = () -> s1.equals(s2);
    System.out.println(stringEquals.getAsBoolean());
Run Code Online (Sandbox Code Playgroud)

作为对此的反对 -

    System.out.println(s1.equals(s2));
Run Code Online (Sandbox Code Playgroud)

Fed*_*ner 6

从理论上讲,我可能使用Suppliers的主要原因是,正如@Eugene在他的回答中所说,推迟执行.但在实践中,我从来没有任何理由BooleanSupplier专门使用.更重要的是,我发现很难想出真实的使用场景......

尽管如此,我认为值得展示一个典型的用法Supplier<String>.我希望这可以说明一般供应商的使用情况.

典型的例子是记录.假设您必须记录返回值的非常昂贵的计算结果,但仅在日志级别设置为时DEBUG.假设这个非常昂贵的计算由该方法表示,该方法veryExpensive()返回一个值(返回类型对于该示例而言并不重要).

传统的使用模式是使用if语句,因此我们只在DEBUG启用日志级别时执行非常昂贵的计算:

if (logger.isDebugEnabled()) {
    logger.debug("veryExpensive() returned: " + veryExpensive());
}
Run Code Online (Sandbox Code Playgroud)

这按预期工作,因为如果将日志级别设置为eg INFO,我们将永远不会调用veryExpensive().但现在想象一下,你的代码遍布了同样的模式.太好了,呃?一个简单的任务,例如日志记录已经用if语句污染了所有代码...(而且我没有发明这个,我实际上已经看过很多次了).

现在想想如果logger.debug接受一个Supplier<String>而不是普通的String价值会发生什么.在这种情况下,我们不再需要该if语句,因为将String值提取到日志的逻辑现在将驻留在logger.debug方法的实现中.使用模式现在是:

logger.debug(() -> "veryExpensive() returned: " + veryExpensive());
Run Code Online (Sandbox Code Playgroud)

哪里() -> "veryExpensive() returned: " + veryExpensive()Supplier<String>.

这非常有效,因为执行veryExpensive()延迟直到logger.debug方法需要实际记录由此String返回的方法Supplier<String>,并且只有在DEBUG启用日志级别时才会发生这种情况.

  • 阅读这个答案让我想起了一些关于一个人的YouTube视频,这个视频解释了你在这里所说的内容以及我最喜欢的Java-8书(Java-8在行动中)也提到了这一点.在发布我的答案时完全忘记了.虽然我上午到凌晨3-4点(可能解释了我的注意力不集中.)+1照常好的详细答案;) (3认同)
  • 嘿@Aominè非常感谢你的客气话.我既没有看过那个视频也没看过那本书,但是我记得看过采用这种方法的一些日志框架,我认为LOG4J 2是这样设计的 (3认同)

Ous*_* D. 1

在这种特定情况下,执行以下操作是没有意义的:

BooleanSupplier stringEquals = () -> s1.equals(s2);
System.out.println(stringEquals.getAsBoolean());
Run Code Online (Sandbox Code Playgroud)

而不仅仅是:

System.out.println(s1.equals(s2));
Run Code Online (Sandbox Code Playgroud)

因此没有任何好处,事实上,后一种方法可以说更容易阅读并且代码更少。

BooleanSupplier任何其他函数接口一样,它只是一个标准,即“要引用的函数的结构必须具有 x 个参数,并且可能会或可能不会返回值”

也就是说, aBooleanSupplier只是一个生成布尔值的原始特化Supplier,因此它的工作最终是向调用者提供一个值(就像一个getter方法)。

因为BooleanSupplier它是一个函数式接口,所以您可以将其作为行为参数化传递给另一个方法,将其作为方法的返回类型,然后您可以在其他地方使用它;以及将其用作不带参数的方法的目标类型,可能会执行一些逻辑并返回结果。

如果在适当的情况下明智地使用,这可以带来良好的好处。