原始流与对象流和发生的实际装箱 [英] Primitive stream vs object stream and actual boxing that occurs
问题描述
所以我知道你可以有对象流,即 Stream< T>
和专家原始流,例如 IntStream
, DoubleStream
等。后者的一个好处是避免自动装箱。
So I understand you can have object streams, i.e. Stream<T>
and specialist primitive streams, e.g. IntStream
, DoubleStream
, etc. One of the benefits of the latter is to avoid autoboxing.
另外,如果我们以 IntStream
为例,它有专门的操作,例如过滤器接受 IntPredicate
。
Also if we take IntStream
as an example, it has specialised operations such as filter that accepts an IntPredicate
.
我想知道我是否有 IntStream
vs a Stream< Integer>
此时您正在保存拳击,例如
I wondered if I had an IntStream
vs a Stream<Integer>
at which point you're saving on boxing, e.g.
intstream.filter(x -> x >= 50).forEach(x -> System.out.println(x));
vs
stream.filter(x -> x >= 50).forEach(x -> System.out.println(x));
在第一个例子中,我看不到装箱或拆箱。在第二个例子中,拳击/拆箱发生在哪里?因为如果stream是 Stream< Integer>
并且过滤器接受 Predicate< Integer>
,那么肯定没有必要box / unbox,同样适用于 IntConsumer
vs Consumer< T>
?
In the first example, there is no boxing or unboxing that I can see. In the second example where is the boxing / unboxing occurring? Because if stream is a Stream<Integer>
and the filter accepts a Predicate<Integer>
then surely there's no need to box/unbox, and the same for IntConsumer
vs Consumer<T>
?
推荐答案
使用 Stream< Integer>
您的信息流已经装箱。因此,根据您创建它的方式,有几种可能性:
With Stream<Integer>
your stream is already boxed. So depending on how you created it there are several possibilities:
-
您最初已装箱值。例如,您有
List< Integer> list
作为输入并写道:
stream = list.stream();
您在创建流时装箱了您的值。例如,您创建如下:
You boxed your values when creating the stream. For example, you created it like this:
stream = Stream.iterate(1, x -> x+1);
在这种情况下,第一个参数被装箱为 Integer.valueOf(1)
和取消装箱/装箱也会发生在每个lambda( UnaryOperator< Integer>
)调用上。所以你有效:
In this case the first argument is boxed to Integer.valueOf(1)
and unboxing/boxing also occurs on every lambda (which is UnaryOperator<Integer>
) invocation. So effectively you have:
stream = Stream.iterate(Integer.valueOf(1), x -> Integer.valueOf(x.intValue()+1));
您通过上游中间操作明确地装箱了您的来源。例如:
You boxed your source explicitly via upstream intermediate operation. For example:
stream = IntStream.range(0, 1000).boxed();
在这种情况下,拳击是在 .boxed()$内执行的c $ c>操作(这是
.mapToObj(Integer :: valueOf)
的快捷方式)。
In this case boxing is performed inside the .boxed()
operation (which is a shortcut for .mapToObj(Integer::valueOf)
).
这篇关于原始流与对象流和发生的实际装箱的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!