将lambdas转换为方法引用

Bal*_*Bal 6 java lambda java-8 java-stream method-reference

有人可以帮我转换下面的代码来使用方法引用吗?我试图绕过这个新语法,但是当它变得比单个变量映射到单个方法调用更复杂时,我很快就会迷失:

getWorkspaces().stream().forEach((ws) -> {
            DataStoreInfo defaultDataStore = getDefaultDataStore(ws);
            if (defaultDataStore != null) {
                other.setDefaultDataStore(ws, defaultDataStore);
            }
        });
Run Code Online (Sandbox Code Playgroud)

我从这开始,但它不起作用:)

getWorkspaces().stream()
               .map(this::getDefaultDataStore)
               .filter(Objects::nonNull)
               .map(other::setDefaultDataStore);
Run Code Online (Sandbox Code Playgroud)

编辑:通过"它不起作用",我的意思是IDE在"setDefaultDataStore"下的最后一行抱怨它无法解析该方法.我希望我能从一些有用的东西开始,但我不知道如何到达那里.我很困惑如何使用方法引用来调用一个带有2个参数的方法以及如何映射它.我已经转换了一些看起来像这样的代码:

 getMaps().stream().forEach((m) -> {
            other.add(m);
        });
Run Code Online (Sandbox Code Playgroud)

对此:

getMaps().forEach(other::add);
Run Code Online (Sandbox Code Playgroud)

但是当它变得更复杂时我会迷失方向.我希望有一个明显的解决方案,如何使用方法引用编写相同的代码.

Mor*_*van 5

您可以在此处阅读有关方法引用的许多有用信息 https://docs.oracle.com/javase/tutorial/java/javaOO/methodreferences.html

如果您的 lambda 仅调用已存在的方法,则可以将其替换为方法引用。因此,如果您对 lambda 感到满意,您将轻松应对方法引用。

它们有4种

  1. 对静态方法的引用 - ContainingClass::staticMethodName
  2. 对特定对象的实例方法的引用 - containsObject::instanceMethodName
  3. 对特定类型的任意对象的实例方法的引用 - ContainingType::methodName
  4. 对构造函数的引用 - ClassName::new

回到你的问题: .map(other::setDefaultDataStore);

您不应该使用 map 函数对流成员执行某些副操作,它用于将流转换为另一个。用户 foreach 代替

getWorkspaces().stream()
               .map(this::getDefaultDataStore)
               .filter(Objects::nonNull)
               .foreach(other::setDefaultDataStore);
Run Code Online (Sandbox Code Playgroud)


Öme*_*den 3

您可以将代码转换为 lambda 版本,如下所示,但它并不像预期的那样干净。

words.stream().map(ws -> new SimpleImmutableEntry<>(ws, getDefaultDataStore(ws)))
              .filter(e -> e.getValue() != null)
              .forEach(e -> setDefaultDataStore(e.getKey(), e.getValue()));
Run Code Online (Sandbox Code Playgroud)

注:e 是entry 的缩写。