【问题标题】:How to map multiple variable in Java lambda? [closed]如何在 Java lambda 中映射多个变量? [关闭]
【发布时间】:2020-11-27 08:45:56
【问题描述】:

我有一个过滤包含枚举的列表的方法 我

if (availableImageSizes.stream()
                       .filter(t -> t.getNameSuffix().equals("-xs"))
                       .findFirst().isPresent())
{
    int width = availableImageSizes.stream()
                       .filter(t -> t.getNameSuffix().equals("-xs"))
                       .findFirst().getWidth();

    int height = availableImageSizes.stream()
                       .filter(t -> t.getNameSuffix().equals("-xs"))
                       .findFirst().getHeight();
}

如您所见,我尝试根据其 NameSuffix 过滤列表,过滤后我想将该值的宽度和高度映射到一个变量。但是代码错了,就算能用,也太难看了。

我可以在一个 lambda 中映射多个变量吗?如果是这样,我该如何实现?

【问题讨论】:

  • 您可以生成两个值的集合,或者一个简单的数组。或者甚至创建自己的类来表示这一点(Pair 类非常流行)。取决于您想做什么以及如何处理。
  • 附带说明,availableImageSizes.stream().filter(t -> t.getNameSuffix().equals("-xs")).findFirst() 可能应该被提取,您可以在其上执行ifPresent,或者在该值上链接or/orElse/etc。无需生成 3 次。

标签: java lambda java-8 java-stream optional


【解决方案1】:

如果您需要将这些值作为方法返回值的一部分

如果有合理的默认值,我会这样做

Optional<ImageSize> xsImageSize = availableImageSizes.stream()
    .filter(t -> t.getNameSuffix().equals("-xs"))
    .findFirst();
int height = xsImageSize.map(ImageSize::getHeight).orElse(-1);
int width = xsImageSize.map(ImageSize::getWidth).orElse(-1);

或者,可以为空的整数

Integer height = xsImageSize.map(ImageSize::getHeight).orElse(null);
Integer width = xsImageSize.map(ImageSize::getWidth).orElse(null);

否则

Optional<ImageSize> xsImageSize = availableImageSizes.stream()
    .filter(t -> t.getNameSuffix().equals("-xs"))
    .findFirst();
if (xsImageSize.isPresent())
{
    int height = xsImageSize.get().getHeight();
    int width = xsImageSize.get().getWidth();
    //...
}

如果您不需要返回这些值

availableImageSizes.stream()
    .filter(t -> t.getNameSuffix().equals("-xs"))
    .findFirst()
    .ifPresent(imageSize -> {
        int height = imageSize.getHeight();
        int width = imageSize.getWidth();
        //...
    });

availableImageSizes.stream()
    .filter(t -> t.getNameSuffix().equals("-xs"))
    .findFirst()
    .ifPresent(this::processXsImageSize);

//...
private void processXsImageSize(ImageSize imageSize) {
    int height = imageSize.getHeight();
    int width = imageSize.getWidth();
    //...
}

【讨论】:

    【解决方案2】:

    首先,您的目标是删除重复代码:

    availableImageSizes.stream()
                       .filter(t -> t.getNameSuffix().equals("-xs"))
                       .findFirst()
    

    我不确定“in one lamba”是什么意思。但是,您可以通过 StreamOptional 方法调用的单个链来实现此目的。但是,您无法一次重新运行两个或多个值。解决方案是将要分解的数组返回到widthheight。最好使用自定义对象Dimension/Point 类或Pair/AbstractMap.SimpleEntry

    数组是显示解决方案的最简单方法。

    Integer[] dimensions = availableImageSizes.stream()
        .filter(t -> t.getNameSuffix().equals("-xs"))                // images with a suffix
        .findFirst()                                                 // Optional<MyImage>
        .map(obj -> new Integer[] {obj.getWidth(), obj.getHeight()}) // map dimensions
        .orElse(new Integer[] {null, null});                         // else default values
            
    Integer width = dimensions[0];                                   // destructured width
    Integer height = dimensions[1];                                  // destructured height
    

    【讨论】:

    • 这可以编译吗?如果将null 分配给int,它不会抛出错误吗?
    • @VLAZ:是的,一个大(对象)Integer 可以为空。小(原始)int 不是。一个真实的事实是widthheight 也应该是Integer,否则可能会返回一个NPE。在任何情况下,它都会编译。如果默认值不是null,而是-1,您可以改用ints——但这取决于OP。
    • 是的,我不清楚这里的最终目标是什么。如果.findFirst 产生一个空结果会发生什么。我个人只是做width = result.map(x -&gt; x.getWidth()).orElse(0)(或任何合理的默认值),因此您不必将结果包装在额外的对象中,但这也取决于结果的去向和处理方式。如果将此结果发送到其他地方,我会尽量避免将Optional 传递给另一个方法。
    • @VLAZ:是的,这是另一种方式,看起来不错。
    • 为什么不availableImageSizes.stream() .filter(t -&gt; t.getNameSuffix().equals("-xs")) .findFirst() .ifPresent(obj -&gt; { int width = obj.getWidth(), height = obj.getHeight(); /* do whatever you want with width and height */ });
    猜你喜欢
    • 2020-09-09
    • 2022-07-14
    • 2018-03-19
    • 2015-06-01
    • 2014-11-23
    • 2020-09-18
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多