在Java8流中,我可以使用mapToInt
方法创建IntStream
,对于某些操作(如OptionalInt
),它将返回findFirst
个。为什么Optional
中没有类似内容?
int i = Stream
.of("1") // just as an example
.mapToInt(Integer::parseInt) // mapToInt exists for streams
.findFirst() // this even returns an OptionalInt!
.getAsInt(); // quite handy
int j = Optional
.of("1") // same example
.map(Integer::parseInt) // no mapToInt available
.get().intValue(); // not as handy as for streams
答案 0 :(得分:7)
显然,Java-9中的Optionals中会出现一些其他方法。但是,mapToInt
不太可能被添加。几天前我在core-libs-dev中discussed出现了这个问题。这是Paul Sandoz answer:
我不想去那里,我的回答是将
Optional*
变换为*Stream
。添加mapOrElseGet
的参数(注意原始变体返回U
)是可以从中组合其他功能。
我认为用Optional来污染OptionalInt等是好的,但是我想避免它用于另一个方向。
总的来说,我认为这是合理的。原始流的目的是在处理许多原始值时提高性能。然而,对于Optional
,使用原始值的性能增益是非常有限的(与流相比,通过JIT编译器进行优化的额外装箱会有更大的机会)。即使项目Valhalla不会出现在Java-9中,它也会逐渐向前发展,并且在Java-10中我们最终可能会看到基本上的泛型,所以这些原语选项将变得完全没必要。在这种情况下,在对象Optional
和原始OptionalInt
之间添加更多的互操作性似乎是不必要的。
答案 1 :(得分:7)
在Stream
API中进行专业化是有道理的,因为流可能代表处理数百万个元素的批量操作,因此性能影响可能非常大。但据我所知,即使这个决定也不是没有争议。
对于最多携带一个元素的Optional
,性能影响并不能证明其他API(如果有任何影响)。目前尚不清楚OptionalInt
等是否真的有必要。
关于方便,我不明白你的观点。以下作品:
int j = Optional.of("1").map(Integer::parseInt).get();
您的建议是添加另一个API,允许将上述语句重写为
int j = Optional.of("1").mapToInt(Integer::parseInt).getAsInt();
我不知道这是如何提高便利性的......
但遵循逻辑,使用Java 9,您可以编写
int j = Optional.of("1").stream().mapToInt(Integer::parseInt).findFirst().getAsInt();
更加提升了这种“便利性”......
答案 2 :(得分:-1)
以下内容也可以很好地工作:
int j = Optional
.of("1")
.map(Integer::parseInt)
.map(OptionalInt::of) // -> Optional<OptionalInt>
.orElse(OptionalInt.empty()) // -> OptionalInt
.getAsInt();
诀窍是将Optional<Integer>
映射到Optional<OptionalInt>
,然后解开内部的OptionalInt
。因此,就Optional
而言,不涉及原始int
,因此它适用于Java泛型。
此方法的一个优点是它不需要自动装箱。这对我来说很重要,因为我们在项目中启用了自动装箱警告,主要是为了防止不必要的装箱和拆箱操作。
我在实现一个返回OptionalInt
的公共方法时偶然发现了这个问题和解决方案,其中实现使用了另一个返回Optional<Something>
的方法。
我不想从公用方法中返回Optional<Integer>
,所以和您一样搜索Optional.mapToInt
之类的东西。
但是,在阅读了 Holger 和 Tagir Valeev 的回复之后,我同意在JDK中省略这种方法是完全合理的。有足够的替代方法。