为什么 Number 的自定义子项不继承自动装箱?
Why do custom children of Number not inherit auto-boxing?
我知道 Java 不支持自定义自动装箱,但我也注意到我可以扩展 Number 对象。由于数字对象本身似乎允许对基元进行自动装箱,因此可行:
Number val = 5; //This compiles no problem
但是,如果我扩展 Number 并尝试使用子类型,程序将无法编译:
MyNumber num = 5; //This does not compile :(
我知道这在 Java 中是不允许的,而且可能永远不会被允许,但是是什么机制导致了这种不连续性的发生? Number 的包装器功能是否在 class 本身之外的某个地方处理,或者是否有一些特殊的封装阻止了自定义包装器的创建?
5 是整数文字。因此它的类型是 int
。
由于它被分配给一个引用类型(数字)的变量,它被自动装箱为其包装器类型:java.lang.Integer
。然后将此整数分配给变量,这是有效的,因为 Integer
是一个 数字:class 整数扩展了 class 数字。
相反,Integer 不扩展 MyNumber。因此,将 Integer 赋值给 MyNumber
类型的变量是无效的:Integer 不是 MyNumber.
所以这和开箱没有太大关系。这与你做不到的事实有关
MyNumber n = someInteger;
就像你不能那样
MyNumber n = someString;
: 类型不兼容。
自动装箱只是一种编译器优化。
语句Integer i= 5;
的实际编译代码是Integer i = Integer.valueOf(5);
这不适用于 Number
的自定义子类,因为编译器不知道它们。您可以使用 IDE 或使用 javap
反编译代码并亲自查看。
我知道 Java 不支持自定义自动装箱,但我也注意到我可以扩展 Number 对象。由于数字对象本身似乎允许对基元进行自动装箱,因此可行:
Number val = 5; //This compiles no problem
但是,如果我扩展 Number 并尝试使用子类型,程序将无法编译:
MyNumber num = 5; //This does not compile :(
我知道这在 Java 中是不允许的,而且可能永远不会被允许,但是是什么机制导致了这种不连续性的发生? Number 的包装器功能是否在 class 本身之外的某个地方处理,或者是否有一些特殊的封装阻止了自定义包装器的创建?
5 是整数文字。因此它的类型是 int
。
由于它被分配给一个引用类型(数字)的变量,它被自动装箱为其包装器类型:java.lang.Integer
。然后将此整数分配给变量,这是有效的,因为 Integer
是一个 数字:class 整数扩展了 class 数字。
相反,Integer 不扩展 MyNumber。因此,将 Integer 赋值给 MyNumber
类型的变量是无效的:Integer 不是 MyNumber.
所以这和开箱没有太大关系。这与你做不到的事实有关
MyNumber n = someInteger;
就像你不能那样
MyNumber n = someString;
: 类型不兼容。
自动装箱只是一种编译器优化。
语句Integer i= 5;
的实际编译代码是Integer i = Integer.valueOf(5);
这不适用于 Number
的自定义子类,因为编译器不知道它们。您可以使用 IDE 或使用 javap
反编译代码并亲自查看。