蒙面博士 2017-08-20 09:22 采纳率: 100%
浏览 1213
已采纳

怎样理解java泛型中的擦除

class GenericBase {
private T element;
public void set(T arg) { arg = element; }
public T get() { return element; }
}

class Derived1 extends GenericBase {}

class Derived2 extends GenericBase {} //这里去除了T,为什么编译时没有问题?

// class Derived3 extends GenericBase<?> {}
// 上面的GenericBase<?>会出现编译错误,这又是为什么?

public class ErasureAndInheritance {
@SuppressWarnings("unchecked")
public static void main(String[] args) {
Derived2 d2 = new Derived2();
Object obj = d2.get();
d2.set(obj); // 如果上面没有@SuppressWarnings修饰的话,这里会出现一个编 译警告,为什么偏偏在set()方法这里出现一个编译警告?
}
}

  • 写回答

6条回答 默认 最新

  • 鼠晓 博客专家认证 2017-08-21 01:21
    关注

    【1】class Derived2 extends GenericBase {} //这里去除了T,为什么编译时没有问题?
    经过测试这种继承方法,是不继承父类泛型效果的,,可能就是题主所说的对父类的泛型擦除

    还可以这样继承,给子类设置泛型,class Derived2 extends GenericBase {},,,和上面一样,父类的泛型效果未被继承

    【2】 class Derived3 extends GenericBase<?> {} 上面的GenericBase<?>会出现编译错误,这又是为什么?
    父类设置了泛型,子类没有泛型,,创建自类时如何给父类设置泛型??所以系统报错“找不到泛型”
    必须给子类和父类设置泛型(且名字相同,测试了一下同时设置 ? 是不行的),
    class Derived2 extends GenericBase(名字随意,但要一样)

    【3】d2.set(obj); // 如果上面没有@SuppressWarnings修饰的话,这里会出现一个编 译警告,为什么偏偏在set()方法这里出现一个编译警告?
    泛型默认是 Object 类型的,,get到一个object不会有问题吧,,,
    set不同,,set需要把你的对象赋值给泛型的对象,,这是有危险的,需要设置泛型才可以取出警告。
    编译器报错,给了个map的例子,大概意思是说“没有指定泛型的地方,赋值都会出现警告。”,,下面有个List的例子:

            List list = new ArrayList();
            list.add("sss");//有警告
    
    

    我也是根据测试结果总结的,欢迎交流,,,,有问题还可以追问
    我的测试代码如下:

     public class TestT {
        //    @SuppressWarnings("unchecked")
        public static void main(String[] args) {
            Derived2<String> d2 = new Derived2<String>();
            Object obj = "aaa";
            d2.set((String) obj);
            System.out.println(d2.get());
    
            List list = new ArrayList();
            list.add("sss");//有警告
    
            GenericBase<String> genericBase = new GenericBase<>();
            genericBase.set("sss");//没警告
        }
    }
    
    class GenericBase<T> {
        private T element;
    
        public void set(T arg) {
            element = arg;
        }
    
        public T get() {
            return element;
        }
    }
    
    class Derived1 extends GenericBase {
    }
    
    class Derived2<S> extends GenericBase<S> {
    }
    
    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论
查看更多回答(5条)

报告相同问题?

悬赏问题

  • ¥60 求一个简单的网页(标签-安全|关键词-上传)
  • ¥35 lstm时间序列共享单车预测,loss值优化,参数优化算法
  • ¥15 基于卷积神经网络的声纹识别
  • ¥15 Python中的request,如何使用ssr节点,通过代理requests网页。本人在泰国,需要用大陆ip才能玩网页游戏,合法合规。
  • ¥100 为什么这个恒流源电路不能恒流?
  • ¥15 有偿求跨组件数据流路径图
  • ¥15 写一个方法checkPerson,入参实体类Person,出参布尔值
  • ¥15 我想咨询一下路面纹理三维点云数据处理的一些问题,上传的坐标文件里是怎么对无序点进行编号的,以及xy坐标在处理的时候是进行整体模型分片处理的吗
  • ¥15 CSAPPattacklab
  • ¥15 一直显示正在等待HID—ISP