你的位置:首页 > Java教程

[Java教程]【Java学习笔记】泛型


泛型:

      jdk1.5出现的安全机制

好处:

  1.将运行时期的问题ClassCastException转到了编译时期。

  2.避免了强制转换的麻烦。

 

<>:

   什么时候用?

      当操作的引用数据类型不确定的时候,就使用<>。将要操作的引用数据类型传入即可。

      其实<>就是一个用于接收具体引用数据类型的参数范围。

 

   在程序中,只要用到了带有<>的类或者接口,就要明确传入的具体引用数据类型。

 

 

泛型技术是给编译器使用的技术,用于编译时期。确保了类型的安全。

 

运行时,会将泛型去掉,生成的class文件中是不带泛型的,这个称为泛型的擦除

  为什么要擦除呢?  为了兼容运行的类加载器。

 

泛型的补偿: 在运行时,通过获取元素的类型进行转换动作。不用 使用者 在强制转换了。

 

泛型的通配符: ? 未知类型

泛型的限定:

  ? extends E:接受E类型或E的子类型对象。上限一般存储对象的时候用。比如,添加元素 addAll        boolean  addAll(<? extends E> c)

  ? super E    :接受E类型或E的父类型对象。下限,一般取出对象的时候用。比如比较器。          TreeSet(Comparator<? super E> comparator)

 

泛型例子:

 1 import java.util.ArrayList; 2 import java.util.Iterator; 3  4 public class GenericDemo { 5  6   public static void main(String[] args) { 7     ArrayList<String> al = new ArrayList<String>(); //强制转化 8      9     al.add("abc");10     al.add("hahah");11 //    al.add(123); //会报错12     13     Iterator<String> it = al.iterator();    //强制转化14     15     while (it.hasNext())16     {17       String str = it.next(); //不用强制转化了18       System.out.println(str);19     }20 21   }22 23 }

 

Comparator,Comparable的泛型

 1 package p2; 2  3 public class Person implements Comparable<Person> { 4   private String name; 5   private int age; 6    7   public Person(){ 8     super(); 9   } 10    11   public Person(String name, int age) 12   { 13     super(); 14     this.name = name; 15     this.age = age; 16   } 17  18   @Override 19   public int compareTo(Person o) { 20 //    Person p = (Person)obj; //不用强制转化了 21     int temp = this.age - o.age; 22  23     return temp==0?this.name.compareTo(o.name):temp; 24   } 25  26   public String getName() { 27     return name; 28   } 29  30   public void setName(String name) { 31     this.name = name; 32   } 33  34   public int getAge() { 35     return age; 36   } 37  38   public void setAge(int age) { 39     this.age = age; 40   } 41  42   /* (非 Javadoc) 43    * @see java.lang.Object#hashCode() 44   */ 45   @Override 46   public int hashCode() { 47     final int prime = 31; 48     int result = 1; 49     result = prime * result + age; 50     result = prime * result + ((name == null) ? 0 : name.hashCode()); 51     return result; 52   } 53  54   /* (非 Javadoc) 55    * @see java.lang.Object#equals(java.lang.Object) 56   */ 57   @Override 58   public boolean equals(Object obj) { 59     if (this == obj) 60       return true; 61     if (obj == null) 62       return false; 63     if (getClass() != obj.getClass()) 64       return false; 65     Person other = (Person) obj; 66     if (age != other.age) 67       return false; 68     if (name == null) { 69       if (other.name != null) 70         return false; 71     } else if (!name.equals(other.name)) 72       return false; 73     return true; 74   } 75  76   /* (非 Javadoc) 77    * @see java.lang.Object#toString() 78   */ 79   @Override 80   public String toString() { 81     return "Person [name=" + name + ", age=" + age + "]"; 82   } 83    84    85  86 } 87  88  89 package p3; 90  91 import java.util.Comparator; 92  93 import p2.Person; 94  95 public class ComparatorByName implements Comparator<Person> { 96  97   @Override 98   public int compare(Person o1, Person o2) { 99     int temp = o1.getName().compareTo(o2.getName());100     101     return temp==0? o1.getAge()-o2.getAge() : temp;102   }103   104 105 }106 107 import java.util.Iterator;108 import java.util.TreeSet;109 110 import p2.Person;111 import p3.ComparatorByName;112 113 public class GenericDemo2 {114 115   public static void main(String[] args) {116     TreeSet<Person> ts = new TreeSet<Person>(new ComparatorByName());117     118     ts.add(new Person("sfsf",21));119     ts.add(new Person("fdg",14));120     ts.add(new Person("erw",18));121     ts.add(new Person("iu",30));122     123     Iterator<Person> it = ts.iterator();124     125     while(it.hasNext())126     {127       Person p = it.next();128       129       System.out.println(p);130     }131 132   }133 134 }

 

 类和方法上的泛型

 1 public class Tool<QQ> { 2   private QQ q; 3  4   public QQ getObject() { 5     return q; 6   } 7  8   public void setObject(QQ object) { 9     this.q = object;10   }11   12   /*13    * 将泛型定义在方法上14    * 15    * */16   17   public <W> void show(W str)18   {19     System.out.println(str.toString());20   }21   22   public void print(QQ str)23   {24     System.out.println(str);  //如果写str.length(); 是错误的;  因为不知道泛型QQ究竟是什么具体类型,所以不能使用具体类型的方法。25                   //不过可以使用Object的方法  26   }27   28   /*29    * 当方法静态时,不能访问类上定义的泛型。30    * 如果静态方法使用泛型,只能将泛型定义在方法上。31    * 泛型一定要放在返回值类型的前面,修饰符的后面32    * 33    * */34   public static <Y> void method(Y obj)35   {36     System.out.println(obj);37   }38   39   40 41 }