方法引用和链式谓词

ytt*_*rrr 2 java predicate java-8 java-stream method-reference

我正在尝试用方法引用来压缩我的代码.这是我要改进的一条线:

assertThat("only true & false strings allowed",
        records.stream().map(Record::getType)
        .allMatch(s -> "true".equals(s) || "false".equals(s)));
Run Code Online (Sandbox Code Playgroud)

使用方法参考,它可以更好:

assertThat("only true & false strings allowed",
       records.stream().map(Record::getType).allMatch("true"::equals));
Run Code Online (Sandbox Code Playgroud)

但是,无论如何我可以在谓词中添加"false"吗?

Sot*_*lis 5

String我所知道的类或JDK中没有方法等同于你的方法Predicate.你可以自定义一个

public static boolean match(String arg) {
    return "true".equals(arg) || "false".equals(arg);
}
Run Code Online (Sandbox Code Playgroud)

并使用它

assertThat("only true & false strings allowed",
   records.stream().map(Record::getType).allMatch(Example::match);
Run Code Online (Sandbox Code Playgroud)

或者您可以使用Pattern正则表达式作为Predicate

assertThat("only true & false strings allowed",
   records.stream().map(Record::getType)
          .allMatch(Pattern.compile("^(false|true)$").asPredicate()));
Run Code Online (Sandbox Code Playgroud)

而且,正如Holger在评论中所建议的那样,你可以使用

.allMatch(Arrays.asList("true", "false")::contains)
Run Code Online (Sandbox Code Playgroud)

或类似的东西Set.

  • 注意`Pattern.predicate`使用`find`而不是`matches`.因此,您需要`^(false | true)$`作为模式来实现*matches*语义. (3认同)
  • 并且与非`String`元素一起使用的解决方案是`.allMatch(Arrays.asList("true","false"):: contains)`(尽管这应该只与少量元素一起使用). (3认同)