java - 像 C++ 风格的函数指针一样使用 Java Lambdas?

标签 java lambda java-8 function-pointers

总的来说,我对 lambda 和 Java8 还很陌生,所以如果这是一个简单的问题,我深表歉意。

我目前有一个类,我想在它的 final 上做一些复杂的匹配,有一堆 setter/getter :

public final class Foo {
  public String getName();
  public Type getType();
  public List<Bar> getBarList();
  ....
}

我编写了一个用于匹配的小辅助类:

public class MatchParameter<T> {
  boolean expectMatch = true;
  T valueToCheck;

  public MatchParameter(T value, boolean shouldMatch) {
    this.expectMatch = shouldMatch;
    this.valueToCheck = value;
  }

  public boolean matches(Predicate<T> matcher) {
    return matcher.test(valueToCheck) == expectMatch;
  }
}

然后我有一个地方可以创建各种 MatchParameters用于检查名称或检查 List<Bar> 之类的事情包含特定的 Bar :

MatchParameter<String> nameParam = new MatchParameter(inputName, shouldMatch);
MatchParameter<Bar> barParam = new MatchParameter(inputBar, shouldMatch);
....

我目前无法记住每个 MatchParameter 的内容在寻找。最终我的检查代码如下所示:

if(nameParam.matches(name -> currentFoo.getName().matches(name)) {
  ...
}
if(barParam.matches(bar -> currentFoo.getBarList().contains(bar)) {
  ...
}
...

在每种情况下,我传递的 Predicate 都是一个具有 currentFoo.<accessorFns> 迭代的 lambda它最终采用类型 T,并返回 boolean 值。我真正想做的是将访问器的逻辑移动到 MatchParameter 的创建中。

有没有一种方法可以指定一个可以在构造时传入的函数指针?我希望它是某种需要 (Foo,T) 的可运行程序.

在 C++ 中,我会添加一个本地函数指针,它接受两个输入,一个 Foo和一个 T , 到 MatchParameter 的局部变量:

 bool (*checkFn)(Foo f, T input);

然后我可以为每个实例化创建一个匿名函数,并更新我的 MatchParameter matches实现为:

public boolean matches(Foo f) {
  return checkFn(f, valueToCheck) == expectMatch;
}

我的实例化是:

MatchParameter<String> nameParam = new MatchParameter<>(
  inputName, 
  shouldMatch, 
  (Foo f, String input) -> boolean { return f.getName().matches(input); }
);

在 Java 中是否有等效的方法来实现此目的?

最佳答案

如果你的函数应该总是返回一个 boolean 值,那么你可以传递一个 BiPredicate 给构造函数:

public class MatchParameter<T> {
    boolean expectMatch = true;

    T valueToCheck;

    BiPredicate<Foo, T> predicate;

    public MatchParameter(T value, boolean shouldMatch, BiPredicate<Foo, T> function) {
        this.expectMatch = shouldMatch;
        this.valueToCheck = value;
        this.predicate = predicate;
    }

    public boolean matches(Predicate<T> matcher) {
        return matcher.test(valueToCheck) == expectMatch;
    }
}

然后您可以按如下方式实例化该对象:

MatchParameter<String> nameParam = new MatchParameter<>(inputName, shouldMatch,
    (foo, input) -> f.getName().matches(input)
);

最后,您可以创建一个函数来测试 BiPredicateFoo 对象:

public boolean matches(Foo f) {
    return predicate.test(f, valueToCheck) == expectMatch;
}

关于java - 像 C++ 风格的函数指针一样使用 Java Lambdas?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/43926295/

相关文章:

java - 领英解析。如何一个接一个地运行任务?

java - 专门的 Optional 类型(OptionalInt、OptionalDouble 等)是否执行堆分配?

java - 没有找到带有 Java 记录和 BeanPropertyRowMapper 的默认构造函数

java - JPA/Hibernate继承没有id

java - 通过ErrorListener累积/收集错误以在解析后进行处理

haskell - 匿名函数概念理解

c# - Predicatebuilder group and or queries with inner outer

java - 使用 Java 8 Optional 实现安全的 Map 遍历

java - Java 8 代码库可以编译并在 Java 6 VM 上运行吗?

java - Spark on yarn jar 上传问题