Java Stream map 和 mapToObj 之间的区别
我感觉不到Java 8 Streams中的方法之间的区别。在这两种情况下,我们都可以创建对象并将其返回到流中,那么为什么这些方法作为两个存在,而不仅仅是一个。map()
mapToObj()
你能给我一个例子解释一下吗?
我感觉不到Java 8 Streams中的方法之间的区别。在这两种情况下,我们都可以创建对象并将其返回到流中,那么为什么这些方法作为两个存在,而不仅仅是一个。map()
mapToObj()
你能给我一个例子解释一下吗?
你会看到这个很酷的模式。这些类包括 、 等。这样,您就可以在流操作中使用基元类型。因为否则,您必须使用 或 ,它将框住值。Stream
IntStream
LongStream
DoubleStream
Stream<Integer>
Stream<Double>
同样,这些方法也这样做。在类中,有 方法,但在 类中情况略有不同。map
Stream<T>
mapToInt
mapToDouble
IntStream
DoubleStream
在 中,该方法采用 一个 ,它将一个 int 映射到一个 int。如果要将流映射到 ,则必须使用 。 是一个好名字,因为它与映射到整数的区别。它表示流从 a 更改为 .之所以这样命名,与为什么这样命名的原因相同 - 表示类型/IntStream
map
IntUnaryOperator
Stream<T>
mapToObj
mapToObj
map
IntStream
Stream<T>
mapToObj
mapToInt
Stream
数据类型的基元和对象版本(即 和 、 和 等)在Java中彼此之间并不真正兼容。它们通过自动装箱/拆箱的额外步骤实现兼容。因此,如果您有一个原始 int 流,并且您尝试使用 和 的对象版本(即 和 ),您将产生装箱和取消装箱元素的费用。int
Integer
double
Double
Stream
Function
Stream<Integer>
Function<Integer, Integer>
为了消除这个问题,函数包包含流的原始专用版本以及功能接口。例如,应使用 而不是 使用 。现在,您可以使用 处理流的每个元素。这将完全避免自动装箱/取消装箱。Stream<Integer>
IntStream
IntFunction
因此,每当要处理基元元素流时,都应使用基元专用流(即 、、和)和基元专用功能接口(即 、、等)来实现更好的性能。IntStream
LongStream
DoubleStream
IntFunction
IntConsumer
IntSupplier
还有一点需要注意的是,没有一个原始的专用功能接口(如 、 、 或 ) 扩展非原始功能接口(即 、 等)。IntFunction
DoubleFunction
IntConsumer
Function
Consumer
java.util.function package
包含 、 和 (但不是 ) 所有功能接口的版本。例如,有一个、一个 DoubleFunction 和一个 ,它们是 函数 的 、 和 版本。这些函数与流的原始专用版本(如 、 和 )一起使用。int
double
long
float
IntFunction
LongFunction
int
double
long
IntStream
DoubleStream
LongStream
让我们举几个例子:
Stream<Object> stream1 = Stream.of(1, 2, 3); //Will compile fine
IntStream intStream1 = IntStream.of(4, 5, 6); //Will compile fine
Stream<Object> stream2 = IntStream.of(4, 5, 6); //Does not compile
Stream<Object> stream3 = IntStream.of(4, 5, 6).mapToObj(e -> e); //mapToObj method is needed
IntStream intStream2 = Stream.of(4, 5, 6).mapToInt(e -> e); //mapToInt method is needed
总而言之,您可能使用的原因与 您可能使用的原因相同,即更改类型。mapToObj
mapToInt
Stream