天天看点

Java.集合.泛型初步

Java.集合.泛型初步

一、JDK5.0新特性 :泛型

1.为什么引入?

  • 可以统一集合中的数据类型
  • 可以减少强制类型转换

2.泛型语法如何实现

  • 泛型是一个编译阶段的语法
  • 在编译阶段统一集合中的元素类型

3.泛型的优缺点

  • 优点:统一类型、减少强制类型转换
  • 缺点:类型过于单一

案例:

import java.util.*;
/*
 * 以下程序未使用泛型的缺点与优点
 *    优点:可以对不同类型的元素存储,调用。
 *    缺点:若集合不使用泛型,则集合中的元素类型不统一。
 *          在遍历集合的时候,只能拿出来Object类型,需
 *          要大量的进行强制类型转换,十分麻烦。
 */
class A{
  public void m1(){
    System.out.println("A's m1()执行了。");
  }
}

class B{
  public void m2(){
    System.out.println("B's m2()执行了。");
  }
}

class C{
  public void m3(){
    System.out.println("C's m3()执行了。");
  }
}

public class GenericTest01 {
  /**
   * @param args
   */
  public static void main(String[] args) {
    // TODO Auto-generated method stub

    //创建一个Set集合
    Set s = new HashSet();
    
    //创建对象
    A a = new A();
    B b = new B();
    C c = new C();
    
    //添加元素
    s.add(a);
    s.add(b);
    s.add(c);
    
    //需求:遍历集合,若A,调用m1方法,以此类推
    Iterator it = s.iterator();
    while(it.hasNext()){
      Object o = it.next();
      if(o instanceof A){
        A a1 = (A) o;
        a1.m1();
      }else if(o instanceof B){
        B b1 = (B) o;
        b1.m2();
      }else if(o instanceof C){
        C c1 = (C) o;
        c1.m3();
      }  
      }
  }
}      

使用了泛型之后

​​​案例一:List—ArrayList(点击-与未使用泛型比较)​​

import java.util.*;

public class GenericTest02 {
  /**
   * @param args
   */
  public static void main(String[] args) {
    // TODO Auto-generated method stub

    //创建一个list集合,只能存储字符串类型
    List<String> strs = new ArrayList<String>();
    
    //添加元素
    //strs.add(1);
    /*
     * Exception in thread "main" java.lang.Error: 
            Unresolved compilation problem: 
        The method add(int, String) in the type List<String> is not applicable for the arguments (int)
     */
    strs.add("无中生有");
    strs.add("暗度陈仓");
    strs.add("草船借箭");
    strs.add("万箭齐发");
    
    //遍历
    Iterator<String> it = strs.iterator();
    while(it.hasNext()){
      String s = it.next();
      System.out.println(s);
    }
  }
}      

​​案例二: Map—HashMap(点击-与未使用泛型比较)​​

import java.util.*;
public class GenericTest03 {
  /**
   * @param args
   */
  public static void main(String[] args) {
    // TODO Auto-generated method stub

    //创建一个Map集合
    Map<String,Integer> maps = new HashMap<String,Integer>();
      
    //存入元素
    maps.put("西瓜", 1);
    maps.put("冬瓜", 10);
    maps.put("哈密瓜", 100);
    maps.put("南瓜", 1000);
    maps.put("甜瓜", 10000);
    
    //遍历
    Set<String> keys = maps.keySet();
    Iterator<String> it = keys.iterator();
    while(it.hasNext()){
      String k = it.next();
      Integer v = maps.get(k);
      System.out.println(k+"--->"+v);
    }
  }
}
冬瓜--->10
哈密瓜--->100
甜瓜--->10000
南瓜--->1000
西瓜--->1      

​​案例三:SortedSet—TreeSet(点击-与未使用泛型比较)​​

import java.util.*;

class Manager implements Comparable<Manager>{

  double salary; //薪水
  
  Manager(double salary){
    this.salary = salary;
  }
  
  public String toString(){
    return salary+""; 
  }
  
  public void work(){
    System.out.println("工作,一个月"+salary+"元");
  }
  
  @Override
  public int compareTo(Manager m) {
      double sal1 = this.salary;
      double sal2 = m.salary; //不需要强制类型转换了
      if(sal1>sal2){
        return 1;
      }else if(sal1<sal2){
        return -1;
      }else{
        return 0;
      }
  }
  
}

public class GenericTest04 {
  /**
   * @param args
   */
  public static void main(String[] args) {
    // TODO Auto-generated method stub

    //创建一个SortedSet集合
    SortedSet<Manager> ss = new TreeSet<Manager>();
    
    //创建Manager对象
    Manager m1 = new Manager(1000.0);
    Manager m2 = new Manager(1500.0);
    Manager m3 = new Manager(2000.0);
    
    //添加元素
    ss.add(m1);
    ss.add(m2);
    ss.add(m3);
    
    //遍历
    Iterator<Manager> it = ss.iterator();
    while(it.hasNext()){
      Manager m = it.next();
      m.work();
    }
  }
}
工作,一个月1000.0元
工作,一个月1500.0元
工作,一个月2000.0元      

二、自定义泛型

方法泛型注意的事项:

1. 在方法上自定义泛型,这个自定义泛型的具体数据类型是在调用该 方法的时候传入实参时确定具体的数据类型的。

2. 自定义泛型只要符合标识符 的命名规则即可, 但是自定义泛型我们一般都习惯使用一个大写字母表示。 T Type E Element

3.在泛型中不能使用基本数据类型,如果需要使用基本数据类型,那么就使用基本数据类型对应的包装类型。

泛型类要注意的事项:

1. 在类上自定义泛型的具体数据类型是在使用该类的时候创建对象时候确定的。

2. 如果一个类在类上已经声明了自定义泛型,如果使用该类创建对象 的时候没有指定 泛型的具体数据类型,那么默认为Object类型

3.在类上自定义泛型不能作用于静态的方法,如果静态的方法需要使用自定义泛型,那么需要在方法上自己声明使用。

import java.util.*;

//自定义泛型
class Myclass<T>{
  public void m1(T t){
    System.out.println(t);
  }
}

public class GenericTest05 {
  /**
   * @param args
   */
  public static void main(String[] args) {
    // TODO Auto-generated method stub

    Myclass<String> ms = new Myclass<String>();
    
    //泛型就是编译期检查类型
    //Error
    //ms.m1(100);
    ms.m1("人外有人");
    
  }
}