java.lang.ClassCastException: class [Ljava.lang.Object; cannot be cast to class [Ljava.lang.Integer; Concatenate/Merge/join two Integer[] Array

huangapple go评论103阅读模式
英文:

java.lang.ClassCastException: class [Ljava.lang.Object; cannot be cast to class [Ljava.lang.Integer; Concatenate/Merge/join two Integer[] Array

问题

我正在尝试将两个Integer[]数组连接/合并并存储在另一个Integer[]中。但是我在运行时遇到以下错误。

    at AllInOnePack.MainClass.AllInOne.main(AllInOne.java:61)```

我的代码如下。

**Main class.java**

```java
static Integer[] hardCodeValues = {1,2,3,4};
static Integer[] userValues = {1,2,3,4};
concatArray = new Integer[hardCodeValues.length+userValues.length];
concatArray = (Integer[]) StreamsFunc.concatenate(hardCodeValues, userValues);

StreamsFunc.java

public static <T> Object[] concatenate(T[] hardCodeValues, T[] userValues) 
{
    return Stream.concat(Arrays.stream(hardCodeValues), Arrays.stream(userValues)).toArray();
}

为什么这不是在编译时发现的错误呢?

英文:

I'm trying to concatenate/merge two Integer[] array and store it in an other Integer[]. But I'm getting bellow error at run time.

Exception in thread &quot;main&quot; java.lang.ClassCastException: class [Ljava.lang.Object; cannot be cast to class [Ljava.lang.Integer; ([Ljava.lang.Object; and [Ljava.lang.Integer; are in module java.base of loader &#39;bootstrap&#39;)
at AllInOnePack.MainClass.AllInOne.main(AllInOne.java:61)

My code is like this.

Main class.java

    static Integer[] hardCodeValus = {1,2,3,4};
    static Integer[] userValue = {1,2,3,4};
    concatArray = new Integer[hardCodeValus.length+userValue.length];
	concatArray = (Integer[]) StreamsFunc.concatenate(hardCodeValus, userValue);

StreamsFunc.java

    public static &lt;T&gt; Object[] concatenate(T[] hardCodeValus, T[] userValue) 
    {
	        return Stream.concat(Arrays.stream(hardCodeValus), Arrays.stream(userValue)).toArray();
    }

During run time I'm getting the error. Why this is not found in compile time then?

答案1

得分: 3

因为您将 concatenate 的结果转换为 Integer[]。如果您移除了这个强制转换,编译器会报错,提示无法将 Object[]concatenate 的返回类型)转换为 Integer[]concatArray 的类型)。

请注意,无参数的 Stream.toArray() 返回的是一个 Object[] 实例,而不是流中包含的元素类型的数组。它不能做到后者,因为由于类型擦除,这是不可能的。

> 返回:
>
> 一个数组,其运行时组件类型为 Object,包含此流的元素

同时请注意,如果 concatenate 将返回一个新数组,那么将 concatArray 初始化为 new Integer[...] 是不必要的。

要修复 concatenate,一种方法是使用带有 IntFunction 参数的 toArray重载版本

public static <T> T[] concatenate(T[] hardCodeValues, T[] userValue, IntFunction<T[]> arrayCreator)
{
    return Stream.concat(Arrays.stream(hardCodeValues), Arrays.stream(userValue))
            .toArray(arrayCreator);
}

用法示例:

var concatArray = concatenate(hardCodeValues, userValue, Integer[]::new);
英文:

> Why this is not found in compile time then?

Because you casted the result of concatenate to Integer[]. Had you removed the cast, there will be a compiler error saying that Object[] (the return type of concatenate), cannot be converted to Integer[] (the type of concatArray).

Note that the parameterless Stream.toArray() returns an instance of Object[], not an array of whatever type of element the stream contains. It can't possibly do the latter because of type erasure.

> Returns:
>
> an array, whose runtime component type is Object, containing the
> elements of this stream

Also note that it is unnecessary to initialise concatArray to new Integer[...], if concatenate is going to return a new array anyway.

To fix concatenate, one way would be to call the overload of toArray with an IntFunction:

public static &lt;T&gt; T[] concatenate(T[] hardCodeValus, T[] userValue, IntFunction&lt;T[]&gt; arrayCreator)
{
    return Stream.concat(Arrays.stream(hardCodeValus), Arrays.stream(userValue))
            .toArray(arrayCreator);
}

Usage:

var concatArray = concatenate(hardCodeValus, userValue, Integer[]::new);

答案2

得分: 1

java.util.stream.Stream.toArray() 返回一个其运行时组件类型为 java.lang.Object 的数组。

但在编译时,根据方法签名,您可以返回 Object 的任何子类,这些子类可以是 java.lang.Integer 类型的子类,也可以不是。

在编译时,代码在方法主体中的方法签名和数据类型方面是语法正确的。

实际的类型检查发生在运行时,即在 concatArray = (Integer[]) StreamsFunc.concatenate(hardCodeValus, userValue); 这一行。

因此,您在运行时会收到异常,而不是在编译时,因为当执行 concatenate 方法时,它实际上返回一个 Object 数组。

英文:

java.util.stream.Stream.toArray() returns an Array whose runtime component type is java.lang.Object.

But at compile time, as per method signature, you can return any subclass of Object which may or may not be assignable from java.lang.Integer type.

At compile time, code is syntactically correct as per method signature and data types in the main method.

Actual type check occurs at runtime at line concatArray = (Integer[]) StreamsFunc.concatenate(hardCodeValus, userValue);

So, you get an exception at Runtime rather than compile time because when concatenate method is executed it actually returns an Object array.

huangapple
  • 本文由 发表于 2023年6月5日 17:16:24
  • 转载请务必保留本文链接:https://go.coder-hub.com/76405003.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定