玩转Java泛型

泛型的基本概念

1.什么时候使用泛型:泛型在Java中有着至关重要的作用,Java中所有的集合都需要使用到泛型。只要在使用类或者接口时,该类或者接口在api文档描述时都带着<>,就需要在使用时定义泛型。其实,泛型无非就是通过<>定义了一个形式参数,专门用于接收具体的引用类型。在使用时,一定要传递对应的实际参数类型。

2.泛型的檫除:泛型是JDK1.5之后出现的,所以为了避免修改JVM,就多了一个泛型的檫除,泛型是之出现在编译期的,运行是并没有泛型,也就是说,编译器会按照<>中的指定类型对元素进行检查,检查不匹配,就编译失败,匹配,就编译通过,通过后,产生的class文件中是没有泛型的,这就成为泛型的擦除

3.泛型的补偿:运行时,可以根据具体的元素对象获取其具体的类型,并用该类型对元素进行自动转换。

泛型的基本使用

 * T--Type -> 通常在比较器上面见到
 * E--Element -> 通常在集合上面见到,或者是自定义的集合
 * K,v--Key,Value —> Map<K,V
泛型分为三种类型:
  • 类的泛型

类的泛型比如在自定义一个集合的使用就需要使用到:class MySet<E>{ ... },下面来个简单的例子

class Myset<E>{
	List<E> list = new ArrayList<E>();
	public boolean add(E e){
		return list.add(e);
	}
	public boolean delete(E e){
		return list.remove(e);
	}
	public boolean replace(E e1,E e2){
		if(!list.contains(e1)){
			return false;
		}
		for (int i = 0; i < list.size(); i++) {
			if(list.get(i).equals(e1)){
				list.remove(i);
				list.add(i, e2);
				break;
			}
		}
		return true;
	}
	public Object[] toArray(){
		return list.toArray();
	}
	public int size(){
		return list.size();
	}
	public E get(int index){
		return list.get(index);
	}
}
	@Test
	public void test2(){
		Myset<String>set = new Myset<String>();
		set.add("老干妈");
		set.add("保济丸");
		set.add("炸牛奶");
		set.delete("aa");
		set.delete("保济丸");
		for (int i = 0; i < set.size(); i++) {
			System.out.println(set.get(i));
		}
		System.out.println("--------");
		set.replace("老干妈", "老干爹");
		set.replace("炸牛奶", "炸地瓜");
		for (int i = 0; i < set.size(); i++) {
			System.out.println(set.get(i));
		}
		/*
			老干妈
			炸牛奶
			--------
			老干爹
			炸地瓜
		 */
	}


  • 方法上的泛型
方法上的泛型也细分为三种,与类捆绑的泛型(相当于前面的类的泛型)、独立于类的泛型、静态方法的泛型

class Show<E>{
	//与类捆绑的泛型
	public void print(E e){
		System.out.println(e);
	}
	//独立与类的泛型
	public <T> void qq(T t){
		System.out.println("qq:"+t);
	}
	//静态方法泛型的使用,不能与类的泛型一致,因为静态是类模板,不能调用对象的实例
	public static <T> void yy(T y){
		System.out.println("yy:"+y);
	}
}
	@Test
	public void test1(){
		Show<String> show = new Show<String>();
		show.print("123");
	}
	
	@Test
	public void test3(){
		Show<Integer>show = new Show<Integer>();
		show.qq("二手苹果");
	}
	
	@Test
	public void test4(){
		Show.yy("石头蚊帐二叉树");
	}

  • 接口中的泛型
接口中的泛型使用与前面的使用也差不多,就是在实现类的时候也需要给一个泛型

public class InteGT {
	public static void main(String[] args) {
		Bill<Integer> b = new billImp<Integer>(); 
		b.showBill(100);
		/*
			以上操作相当于
			List<Integer>list = new ArrayList<Integer>();
			list.add(10);
		 */
	}
}
//接口
interface Bill<E>{
	void showBill(E e);
}
//实现类
class billImp<E> implements Bill<E>{
	@Override
	public void showBill(E e) {
		System.out.println("下一站:茶山刘"+e);
	}
}

泛型的高级应用

高级泛型使用通配符?来表示

当操作的不同容器中的类型都不确定的时候,而且使用的都是元素从Object类中继承的方法, 这时泛型就用通配符?来表示即可。(助理解的比方: 泛型中的多态应用)

	@Test
	public void test2(){
		Set<Integer>set1 = new HashSet<Integer>();
		set1.add(1);
		set1.add(2);
		set1.add(3);
		set1.add(4);
		
		Set<String>set2 = new HashSet<String>();
		set2.add("闪电侠");
		set2.add("蝙蝠侠");
		set2.add("钢铁侠");
		set2.add("蜘蛛侠");
		
		printAllSet(set1);
		printAllSet(set2);
	}
	/**
	 * 兼容所有,相当于多态中的Object
	 * @param set
	 */
	public void printAllSet(Set<?>set){
		for (Object object : set) {
			System.out.println(object);
		}
	}

泛型的上下兼容:泛型有上限和下限之分

对操作的类型限制在一个范围之内。比如:定义一个功能,只操作Person类型或者Person的子类型。这时可以用:  
? extends E:接收E类型或者E的子类型。这就是上限。

? super E:   接收E类型或者E的父类型。 这就是下限。

这里就演示一下泛型的上限

@Test
	public void test1(){
		Set<Person>set = new HashSet<Person>();
		set.add(new Student("Bally", 18, "计算机"));
		set.add(new Student("Sammi", 19, "商务英语"));
		set.add(new Student("Oliv", 20, "射箭"));
		
		set.add(new Worker("老干爹", 53, "卖老干妈"));
		set.add(new Worker("老干妈", 52, "卖老干爹"));
		set.add(new Worker("老王", 54, "吃老干妈"));
		
		print(set);
	}
class Person{
	public String name;
	public int age;
	
	public Person(String name,int age){
		this.name = name;
		this.age = age;
	}
}
class Student extends Person{
	String specialty;
	public Student(String name, int age,String specialty) {
		super(name, age);
		this.specialty = specialty;
	}
}
class Worker extends Person{
	String job;
	public Worker(String name, int age,String job) {
		super(name, age);
		this.job = job;
	}
}


  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值