Guava可选类型,当转换返回另一个Optional时

时间:2012-10-25 14:44:19

标签: java generics guava

我有一种方法可以获得Optional<String>

但是这个String必须在另一个应用程序级别解析为Integer或Long。

我有一个Function<String, Integer>可以应用于String,以生成一个Integer。 此转换可能会失败,因为String可能不是Integer可解析值。


我希望在转换失败时返回Optional,而不是抛出解析异常。

我不能让STRING_TO_INTEGER_FUNCTION返回null,因为Guava不允许它:

Exception in thread "main" java.lang.NullPointerException: Transformation function cannot return null.

因此,我唯一可以做的就是拥有Function<String,Optional<Integer>>,但我得到Optional<Optional<Integer>>的最终结果,这并不是很酷,因为我可能有另一个转换应用于它。


有人知道我怎么能在番石榴中做那样的事情?

Optional.of("Toto").transform(STRING_TO_INTEGER_FUNCTION) = // Optional<Integer> ?

由于

3 个答案:

答案 0 :(得分:6)

我想你可以做到:

public static void main(final String[] args) {
  final Optional<Integer> valid = Optional.of("42")
      .transform(STR_TO_INT_FUNCTION)
      .or(Optional.<Integer>absent());
  System.out.println(valid); // Optional.of(42)
  final Optional<Integer> invalid = Optional.of("Toto")
      .transform(STR_TO_INT_FUNCTION)
      .or(Optional.<Integer>absent());
  System.out.println(invalid); // Optional.absent()
  final Optional<Integer> absent = Optional.<String>absent()
      .transform(STR_TO_INT_FUNCTION)
      .or(Optional.<Integer>absent());
  System.out.println(absent); // Optional.absent()
}

private static final Function<String, Optional<Integer>> STR_TO_INT_FUNCTION =
    new Function<String, Optional<Integer>>() {
      @Override
      public Optional<Integer> apply(final String input) {
        return Optional.fromNullable(Ints.tryParse(input));
      }
    };

当您使用Optional - &gt;时,使用笨拙变换 - &gt;或者在一行中(指定转换的可选整数将产生Optional<Optional<Integer>>)。

答案 1 :(得分:5)

使用Optional.transform似乎与可能失败的转换不兼容 - 理论上这意味着可选可选,当你想要做的是合并缺席时。我建议使用以下内容:

Optional<String> strOptional = Optional.of("Toto");
Optional<Integer> intOptional =
        strOptional.isPresent()
        ? Optional.fromNullable(Ints.tryParse(strOptional.get()))
        : Optional.<Integer>absent();

答案 2 :(得分:1)

除上述选择之外的其他选择:

  • 使用普通的if / else(Guava团队建议不要过度使用这些构造,遵循这些建议通常是明智的 - 否则你不会遗漏太多代码并使可读性变差)
  • 使用肮脏的技巧:from(singleton("Toto")).transform(STRING_TO_INTEGER_FUNCTION).filter(notNull()).first().orNull() - 只有假设的想法,恕我直言,它的可读性也很差。至少它不包含任何泛型,?:运算符或匿名类,代价是更多的静态导入。
  • 等待Java 8,其中Optional.map允许空转换结果

您可以投票http://code.google.com/p/guava-libraries/issues/detail?id=1171。不幸的是,Guava团队似乎对将此问题转移到某些结果犹豫不决。