Optional 和 Function 的使用

Usage of Optional and Function

我无法理解 Java 中可选 class 的用法 8. 我想创建一个 class 的实例(所以我会使用供应商)和然后使用 .map() (所以我需要一个可选的)来得到另一件事。我的目的是以一种更“实用”的方式写作。 例如,我有这个代码:

public class ParentClass {

    public static Supplier<Optional<Something>> createSomething = () -> {
        Something sth = new Something();
        sth.setAttribute(“value”);
        return Optional.of(sth);
    }

    public static Function<Optional<Something>, Optional<Something>> doSomething = var -> {
        Something sth = var.get();
        sth.setAnotherAttribute(“anotherValue”);
        return Optional.of(sth);
    }
}

我想这样使用它:

public class ChildClass extends ParentClass{

    public Optional<Something> method(){
        Optional<Something> sth = ParentClass.createSomething.get()
            .map(ParentClass::doSomething);
        return sth;

    }
}

出现错误:

The method map(ParentClass::doSomething) is undefined for the type Something

我不明白为什么会这样。我尝试删除 Optional 包装器,但仍然收到错误消息。还尝试在同一个 ChildClass 文件中编写函数 doSomething 但没有任何反应。你能看出我做错了什么吗? 谢谢

正如 指出的那样,doSomething 已经是 Function;您不需要方法引用语法。此外,map() 需要 Something 上的函数,而不是 Optional<Something> 上的函数。如果你想使用方法引用,它看起来像这样:

public static Something doSomething(Something sth) {
    sth.setAnotherAttribute("anotherValue");
    return sth;
}

Optional::map

的用法示例

使用 lambda 映射

class Test {
  private Function<Integer, String> convert = value -> value.toString();

  public static void main(String[] args) {
    var result = Optional.of(1).map(convert);
    // result now contains Optional with string "1"

    // Or alternatively
    var alternative = Optional.of(1).map(value -> value.toString());
  }
}

地图使用方法参考

class Test {
  public static String convert(Integer value) {
    return value.toString();
  }

  public static void main(String[] args) {
    var result = Optional.of(1).map(Test::convert);
    // result now contains Optional with string "1"

    // Or alternatively
    var alternative = Optional.of(1).map(Objects::toString);
  }
}

请注意,lambda 函数和方法都不会消耗或产生包装在 Optional 中的值。

Optional::map 然后以这种方式工作,如果存储在 Optional 中的值不是 null 那么它将应用于它提供的函数并且其结果将再次换行到 Optional 这将 return.

您的 ParentClass 除了两个静态字段成员外不包含任何方法,这有点令人困惑。

为此,您不能通过方法引用使用 doSomething。您必须致电 doSomething.apply(Optional<Something>)

因此,ChildClass 必须看起来像

public class ChildClass extends ParentClass {

   public Optional<Something> method() {
      Optional<Something> sth = ParentClass.doSomething.apply(ParentClass.createSomething.get());
      return sth;
   }
}

补充

根据您的进一步问题,您可以使用此解决方案。它看起来有点奇怪但有效。

public class ParentClass {

    public static Optional<Something> createSomething() {
        Something something = new Something();
        something.setAttribute("value");
        return Optional.of(something);
    }

    public static Something doSomething(Something something) {
        something.setAnotherAttribute("anotherValue");
        return something;
    }

    public static Something doMoreSomething(Something something) {
        something.setAnotherAttribute("anotherValue");
        return something;
    }
}

如果您使用静态方法,则 ChildClass 不需要从 ParentClass 继承。

public class ChildClass {

    public Optional<Something> method() {

        Optional<Something> something = ParentClass.createSomething().map(ParentClass::doSomething)
                .map(ParentClass::doMoreSomething);

        return something;
    }
}

您的 doSomething 方法必须使用 Something 而不是 Optional<Something> 因为 Optional.map 使用内部 Optional 的包装值。如果你有一个空的 Optionalmap 不会被执行。请注意,根据您的 doSomething 方法的 return,map 可能 return 不同于 Optional<Something>,但它将是一个 Optional.

补充 2

此处 ChildClass 对 ParentClass 非静态方法使用继承。

public class ChildClass extends ParentClass {

    public Optional<Something> method() {

        Optional<Something> something = createSomething().map(this::doSomething).map(this::doMoreSomething);

        return something;
    }
}