A股上市公司传智教育(股票代码 003032)旗下技术交流社区北京昌平校区

 找回密码
 加入黑马

QQ登录

只需一步,快速开始

© 凡延海 中级黑马   /  2012-5-29 23:36  /  2659 人查看  /  5 人回复  /   0 人收藏 转载请遵从CC协议 禁止商业使用本文


  1. <P>public class GenericTest {
  2. public static <T extends Number/*Object*/ > void printGeneric(T...args)
  3. {
  4.   for(T arg:args)
  5.   {
  6.    System.out.println(arg);
  7.    
  8.   }
  9. }
  10. public static void main(String [] args)
  11. {
  12.   Integer [] integer=new Integer[]{1,2,3};
  13.   printGeneric(new int[]{1,2,3});
  14. }
  15. } </P>
复制代码
我用<T extends Number>做测试则的时候 printGeneric(new int[]{1,2,3})会出问题,我用<T extends Object>的时候呢就不会出问题。int[]数组中的数据不是要自动封装成Integer对象的么,怎么在用<T extends Number>时候就出错了呢,而在用<T extends Object>的时候没有出错呢。


评分

参与人数 1技术分 +1 收起 理由
贠(yun)靖 + 1

查看全部评分

5 个回复

倒序浏览
你现在能思考出这个问题有很厉害啊,在java高新技术里面反射那一章你将深入的了解,当你理解了反射后再来理解就会很简单了,我简单说下:数组这种类型很特别,它不像int是原始数据类型,也不是引用数据类型,它就是数组这种类型的。
int [] a1 = new int[]{1,2,3};
a1.getClass().getSuperclass().getName())----->java.lang.Object

可变参数内部其实也是用的数组,这又涉及到jdk5.0兼容性的问题,当你传递了一个数组时,那边把它看成一个对象了,就是数组对象你传过去,相当于Object数组第一个元素接受的是一个数组也就是
Object args[0] =a1;
所以你打印的是 [I@152b6651 数组类型的
当你把参数改为Number类型的,这就是引用类型的了对应的int应该为Integer才能接受,至于你说的自动封装为Integer是指的数组里面的元素单个取出来的时候视具体情况可能会,但是作为int[] 是无法作为Number的,也就是说:
Number args[0] =a1;//cannot convert from int[] to Number
你理解了吗?确实有点绕。

评分

参与人数 1技术分 +1 收起 理由
贠(yun)靖 + 1

查看全部评分

回复 使用道具 举报
楼主想说的可能是自动装箱的功能吧
Integer是继承Number,所以不会出错,而int属于基本类型,如果 int i=5; Integer ig= i;会自动装箱;
而new int[]{1,2,3}这个数组本身就是一个对象,不会出现把int数组转换为Integer数组的情况;
回复 使用道具 举报
数组不会自动拆箱装箱
回复 使用道具 举报
int是基本类型。它并不一个类,所以它也就不会存在 extends Number 类的关系。
Number类的子类有:AtomicInteger, AtomicLong, BigDecimal, BigInteger, Byte, Double, Float, Integer, Long, Short
所以必须要写成与它相关的子类才可以。这里面的<T extends Number>  传人的参数可以是上面的任意子类的类型。编译器不会报错。
你给它传人int类型的数组,当然会编译不通过,因为int类型不符合<T extends Number>这种关系。

当<T extends Object> 时,编译器会把数组当作是一个对象,满足了这种继承关系,所以编译通过。就不会报错了。

回复 使用道具 举报
嗯,数组本身就是一个引用对象不属于Number类型。
回复 使用道具 举报
您需要登录后才可以回帖 登录 | 加入黑马