将char数组分配给int数组

时间:2011-08-08 16:30:22

标签: java arrays

有人可以解释为什么下面代码中的最后一项作业无效

类ScjpTest扩展BounceObject实现了Bouncable {

static int ac = 5;
static char ab = 'd';

static int[] a = new int[]{1,2,3};
static int[] b = new int[]{1,2,3};
static char[] c = new char[]{'a','b'};

public static void main(String[] args){  
    a = b;
    b = a;

    ac = ab;  //This is accepted
    a = c;    //This is rejected
}

}

编译器抱怨以下错误

ScjpTest.java:10: incompatible types
found   : char[]
required: int[]
                a = c;
                    ^
1 error

以下也被接受

class Animal{}
class Horse extends Animal{]

Animal[] animals = new Animal[2];
Horse[] horses = new Horses[2];

animals = horses;

为什么我不能将char数组赋给int数组?

3 个答案:

答案 0 :(得分:8)

因为语言规范禁止它。它在运行时工作以将String []视为Object [],因为它们在内存中具有相同的表示。但是char []和int []有不同的内存表示,如果int []上的每个操作都必须检查它是否真的是伪装的char [],那就慢得令人无法接受。

引用类型的数组必须对赋值执行运行时检查,以便知道是否抛出ArrayStoreException,但至少从它们读取与元素类型无关。

答案 1 :(得分:4)

数组本身就是一个类型,并且转换的工作方式与原语不同。因此,您必须循环所有元素并将它们分配给另一个数组的相应元素。

答案 2 :(得分:1)

您可以将char变量分配给int变量,因为编译器应用扩展转换。基础是int大于char,因此转换中不存在丢失信息的可能性。如果您尝试将int分配给您的char,您会注意到编译器拒绝您的代码,直到您进入特定的类型转换。这是因为缩小转换几乎总是涉及数据丢失,因此编译器要求程序员明确指出这是你打算做的事情。

同样的原则适用于对象。允许扩大转换是隐含的,缩小转换需要进行类型转换。请注意,任何时候都不能通过超类/子类层次结构转换彼此不相关的对象。

Number n = null;
Integer i = null;

n = i ;         // Allowed without casting, Number is superclass of Integer
i = n;          // Compiler error, Integer is sub-class of Number
i= (Integer)n;  // Allowed due to the type-cast

在上面的示例中,Number是Integer的超类。在没有类型转换的情况下,允许将Integer实例分配给Number实例,因为这是一个“扩展”转换。将Number实例分配给Integer实例需要特定的转换,因为这是一个缩小的转换(Number可能代表Float或其他一些子类)。这些规则延续到数组。因此,您可以执行以下操作:

Number[] numArr = null;
Integer[] intArr = null;

numArr = intArr;
intArr = numArr;              //Compile error
intArr = (Integer[]) numArr;

对于原始数组,在数组元素上有 no 扩展转换,即使在你认为它有意义的情况下(即char到int,或字节到char等)。虽然这看起来似乎没有意义,但如果你看一下类似的对象,它就会变得更加清晰:

Double[] doubleArr = null;
Integer[] intArr = null;

doubleArr = intArr ;      // Compile error, Double,Integer are sibling classes
doubleArr = (Double[]) intArr;  // Compile error, same reason
intArr = doubleArr;             // Compile error, same reason
intArr = (Integer[]) doubleArr; // Compile error, same reason

你不能将Double转换为整数,反之亦然,从编译器的角度来看,它们是完全不同的类(例如,与String和Float不同)。