• 泛型擦除


    一句话总结:泛型只在编译期生效!运行期不起作用!

     

    先介绍问题,再引申到理论,比死记理论要好。最近要封装一个通用DAO类,理所当然想到使用泛型,这样不同业务Service调用此DAO类就不用再转换Entity类:

    public class CommonDao<T> {
    
        private EntityManager entityManager;
    
        public T findById(String id) {
            // 重点:这里T.class会报错,这里是问题
            return (T) this.entityManager.find(T.class, id);
        }
    }
    
    // Service示例,CommonDao传入具体类型,方法无需类型转换
    public class CatService {
    
        private CommonDao<CatEntity> commonDao;
    
    }
    
    public class DogService {
    
        private CommonDao<DogEntity> commonDao;
    
    }

    问题出在T.class这里会报错,自己试了几下不行,网上找了下如何获取泛型class,有说用内部类,有说用继承+反射,但其实还是要在封装类中传入具体类型,只不过再隔了一层,若要传入具体类型,那还要泛型干啥,固均不实用。看了spring的HibernateTemplate的get方法,也是需要用户传入具体类class的。固只能给findById方法增加参数,传入具体类class。

      

    结论:

    泛型只在编译期起作用,编译完成后由JVM的类型擦除机制(见引用)擦除泛型,运行期看不到泛型信息,已被替换为具体类型。(其实不是完全擦除,但泛型实现其实很复杂,我们不需要了解那么深,按这样理解就行!)

    引用:

    https://docs.oracle.com/javase/tutorial/java/generics/erasure.html

    https://docs.spring.io/spring/docs/2.5.x/javadoc-api/org/springframework/orm/hibernate3/HibernateTemplate.html

  • 相关阅读:
    android中正确保存view的状态
    使用AudioTrack播放PCM音频数据(android)
    【录音】Android录音--AudioRecord、MediaRecorder
    (原创)初识cordova(一)
    忽略git中不需要进行版本管理的文件
    GitHub 小试
    通过View.post()获取View的宽高
    org.json.JSONObject的getString和optString使用注意事项
    android---EditText的多行输入框
    【转】我赌5毛你没见过这样的SpannableString
  • 原文地址:https://www.cnblogs.com/yuzhengzhong/p/9697879.html
Copyright © 2020-2023  润新知