zoukankan      html  css  js  c++  java
  • 泛型 总结


    介绍
    泛型:jdk1.5出现的安全机制。
    好处:将运行时期的问题ClassCastException转到了编译时期,避免了强制转换的麻烦。
    什么时候用:
    当操作的引用数据类型不确定的时候。就使用<>。将要操作的引用数据类型传入即可。
    其实<>就是一个用于接收具体引用数据类型的参数范围。
    在程序中,只要用到了带有<>的类或者接口,就要明确传入的具体引用数据类型。

    泛型技术是给编译器使用的技术,用于编译时期。确保了类型的安全。
    运行时,会将泛型去掉,生成的class文件中是不带泛型的,这个称为泛型的擦除。
    为什么擦除呢?因为为了兼容运行的类加载器。
    泛型的补偿:在运行时,通过获取元素的类型进行转换动作。不用再强制转换了。

    泛型的通配符【?】未知类型。
    泛型的限定:
    【? extends E】接收E类型或者E的子类型对象。上限。一般存储对象的时候用。比如 添加元素 addAll。
    【? super E】接收E类型或者E的父类型对象。下限。一般取出对象的时候用。比如比较器。

    泛型由来
    Java语言类型包括八种基本类型和复杂类型,复杂类型包括类和数组。
    早期Java版本(1.4之前)如果要代指某个泛化类对象,只能使用Object,这样写出来的代码需要增加强转,而且缺少类型检查,代码缺少健壮性。在1.5之后,Java引入了泛型(Generic)的概念,提供了一套抽象的类型表示方法。利用泛型,我们可以:
    1、表示多个可变类型之间的相互关系:HashMap<T,S>表示类型T与S的映射,HashMap<T, S extends T>表示T的子类与T的映射关系
    2、细化类的能力:ArrayList<T> 可以容纳任何指定类型T的数据,当T代指人,则是人的有序列表,当T代指杯子,则是杯子的有序列表,所有对象个体可以共用相同的操作行为
    3、复杂类型被细分成更多类型:List<People>和List<Cup>是两种不同的类型,这意味着List<People> listP = new ArrayList<Cup>()是不可编译的。后面会提到,这种检查基于编译而非运行,所以说是不可编译并非不可运行,因为运行时ArrayList不保留Cup信息。另外要注意,即使People继承自Object,List<Object> listO = new ArrayList<People>()也是不可编译的,应理解为两种不同类型。因为listO可以容纳任意类型,而实例化的People列表只能接收People实例,这会破坏数据类型完整性。
    4、简化代码实现:假设有一个执行过程,对不同类型的数据,进行某些流程一致的处理,不引入泛型的实现方法为:

    泛型的定义与使用
    public class Test {
        public static void main(String[] args) {
            Person<Boolean> person = new Person<Boolean>();
            System.out.println(person.getValue());
            person.setValue(true);
            System.out.println(person.getValue());
            person.show("包青天");
            Person.staticShow(9);
            InterImpl<Date> in2 = new InterImpl<Date>();
            in2.show(new Date());//重写的方法  Tue Sep 27 17:06:47 CST 2016
        }
    }
    class Person<QQ> { //将泛型定义在【类】上。作用范围为本类中
        private QQ q//QQ代表要操作的引用数据类型
        public QQ getValue() {
            return q;
        }
        public void setValue(QQ q) {
            this.q = q;
        }
        public <W> void show(W str) {//将泛型定义在【方法】上,作用范围为本方法中。放在返回值之前
            System.out.println(str.toString());
        }
        public static <Y> void staticShow(Y obj) {//当方法位静态时,不能访问类上定义的泛型。如果要使用泛型,只能将泛型定义在方法上
            System.out.println(obj);
        }
    }
    //******************************************************************************************
    interface Inter<T> {//将泛型定义在【接口】上
        public void show(T t);
    }
    class InterImpl<Q> implements Inter<Q> {
        public void show(Q q) {
            System.out.println("重写的方法  " + q);
        }
    }

    泛型的限定
    public class Test {
        public static void main(String[] args) {
            ArrayList<Object> al = new ArrayList<Object>();
            al.add("白乾涛");
            al.add(true);
            al.add(20094);
            printCollection(al);

            ArrayList<Student> al2 = new ArrayList<Student>();
            al2.add(new Student("白乾涛"));
            al2.add(new Student("包青天"));
            printCollection2(al2);
        }
        public static void printCollection(Collection<?> al) { //【?】代表可以是未知类型。这里的通配符效果其实和泛型一致
            Iterator<?> it = al.iterator();
            while (it.hasNext()) {
                System.out.println(it.next().toString());
            }
        }
        public static <T> void printCollection2(Collection<T> al) {
            Iterator<T> it = al.iterator();
            while (it.hasNext()) {
                System.out.println(it.next());
            }
        }
        public static void printCollection3(Collection<? extends Person> al) {//【? extends E】接收E类型或者E的子类型对象。【? super E】接收E类型或者E的父类型对象
            Iterator<? extends Person> it = al.iterator();
            while (it.hasNext()) {
                System.out.println(it.next());
            }
        }
    }
    //************************************************************************************
    class Person {
        public String name;
        public int age;
        public Person(String name, int age) {
            super();
            this.name = name;
            this.age = age;
        }
        @Override
        public String toString() {
            return name + "-" + age;
        }
    }
    class Student extends Person {
        public Student(String name) {
            super(name, 26);
        }
    }





  • 相关阅读:
    史玉柱语录
    马云语录
    打开IE窗口自动最大化效果
    两个DIV平行存放
    学习ExtJS(一)
    30而立男人必须明白的事
    学习ExtJS(二) Button常用方法
    UltraWebGrid控件在开发ASP.NET项目中的使用方法和技巧(转)
    GridView模板列DropDownList当前行索引
    TreeView触发TreeNodeCheckChanged事件
  • 原文地址:https://www.cnblogs.com/baiqiantao/p/63a7943d495ef5deca4025362626f033.html
Copyright © 2011-2022 走看看