java泛型总结

通过《码出高效:JAVA开发手册》p164-168页学到了和博客园https://www.cnblogs.com/coprince/p/8603492.html以下知识点:
泛型在java中有很重要的地位,在面向对象编程以及各种设计模式都有广泛的应用!
***1.***泛型即“参数化类型”,一提到参数我们都能想到定义一个方法时括号里的参数是形参,当我们调用此方法时,在括号里面写入的就是实参。例如:

//定义一个方法
    void show( int a){
     Sysotem.out.println(“我想变得优秀!"+"+"+a);
     }

此时在show方法里面,a代表形参,int是参数类型,指定a转入的必须是int类型!
当我们调用方法时填入括号里面的就是实参了!例如:

 Person p=new Person();
 p.show(1);

此时show()方法括号里面的1就是实际参数,指的就是具体的值。
泛型的本质是是为了参数化类型(通过泛型指定不同的类型来控制形参具体限制的类型)操作的数据类型被指定为一个参数,这种参数类型可以用在类、接口和方法中,分别被称为泛型类、泛型接口、泛型方法。
2.
// 第一段 泛型出现之前:集合的定义方式
List a1= new ArrayList();
a1.add(new Object());
a1.add(new Integer(111));
a1.add(new String(“hello ala l”) );
/**
* 第一段说明在没有泛型之前,随便往里面添加什么类型的值都是可以的
* 但是如果你要将这个list转换为某种类型那么就会出现类转换异常ClassCastException
*例如下面的例子:
*/

	String inta=(String)a1;

// Cannot cast from List to String 原意是:list不能转换为String
// 第二段 把a1引用赋值给a2 注意a1与a2的区别是a2增加了泛型限制
List a2 = a1 ;
a2.add(new Object ());
a2.add(new Integer( 222 ));
a2.add(new String ("hello a2a2 "));
List,即原始类型,其引用变量可以接受任何对应List的参数化类型, 包括List<?>,并且可以添加任意类型的元素。但其缺点在于不安全性、不便利性、不表述性(不应该使用原生类型的原因)。
List,即实际类型参数为Object的参数化类型,其引用变量可以接受List,可以添加元素,但不能接受除了其本身外的任何参数化类型(泛型的子类型化原则)。
3.

//第一段:声明第三个依次继承的集合:Object>动物>猫>加菲猫  三个泛型集合可以理解为三个不同的笼子
		List<Animal> animal = new ArrayList<Animal>();        //动物
		List<Cat> cat = new ArrayList<Cat>();				  //猫
		List<Garfield> garfield = new ArrayList<Garfield>();  //加菲猫
<? extends T>可以赋值给任何T及T子类的集合 ,上界为T, 取出来的类型带有

泛型限制 ,向上强制转型为T. null 可以表示任何类型,所以除 null 外,任何元素都
不得添加进<? extends T> 集合内。代码如下:

//第二段:测试赋值操作  以Cat为核心,因为它既有子类又有父类
		//下行编译出错。只能赋值Cat或Cat子类集合
		List<? extends Cat> extendsCatFromAnimal = animal;
		List<? extends Cat> extendsCatFromCat = cat;
		List<? extends Cat> extendsCatFromGarfield = garfield;
		
		
		//第三段:测试add方法
		//下面三行中所有的<? extends T>都无法进行add操作,编译出错
		extendsCatFromCat.add(new Animal());
		extendsCatFromCat.add(new Cat());
		extendsCatFromCat.add(new Garfield());
		extendsCatFromCat.add(null);//除了null之外,其他元素都不能添加进去
		


<? super T>可以赋值给任何T及T的父类集合,下界为T。在生活中,投票选
举类似于<? super >的操作。代码如下:

第四阶段
 List<? super Cat> superCatFromAnimal = animal;
    List<? super Cat> superCatFromCat = cat;
    //下行编译出错。只能赋值Cat或着Cat父类集合
    List<? super Cat> superCatFromGarfield = garfield;
    	//下行编译出错。只能添加Cat或者Cat的子类集合。
    	superCatFromCat.add(new Animal());
    	superCatFromCat.add(new Cat());
    	superCatFromCat.add(new Garfield());

https://www.jianshu.com/p/d4c00768d776博客园和https://blog.csdn.net/JIUTIANDEYING/article/details/80159259 CSDN,扩展泛型类,泛型接口,泛型方法以及常见的集合。。
泛型类
把泛型定义在类上
格式:public class 类名<泛型类型1,…>
注意:泛型类型必须是引用类型
代码如下:

// 泛型类:把泛型定义在类上 
public class ObjectTool<T> { 
      private T obj; 
      public T getObj() { 
         return obj; 
      } 
      public void setObj(T obj) { 
           this.obj = obj;
     }
}
//  泛型类的测试 
public class ObjectToolDemo { 
    public static void main(String[] args) { 
        ObjectTool<String> ot = new ObjectTool<String>();    
        ot.setObj(new String("中国")); 
        String s = ot.getObj(); 
        System.out.println("姓名是:" + s); 
        ObjectTool<Integer> ot2 = new ObjectTool<Integer>();    
        ot2.setObj(new Integer(69)); 
        Integer i = ot2.getObj(); 
        System.out.println("年龄是:" + i); 
   }
}

输出结果:
姓名是:中国
年龄是:69

泛型方法
把泛型定义在方法上
格式:public <泛型类型> 返回类型 方法名(泛型类型 .)
代码如下:

// 泛型方法:把泛型定义在方法上 
    public class ObjectTool {  
          public <T> void show(T t) {
               System.out.println(t); 
          }
    }
      public class ObjectToolDemo { 
            public static void main(String[] args) { 
                 // 定义泛型方法后
                ObjectTool ot = new ObjectTool(); 
                ot.show("hello"); 
                ot.show(100);
                ot.show(true);
           }
      }
    //  这样我们就可以传递任意类型的参数了

泛型接口
把泛型定义在接口上
格式:public interface 接口名<泛型类型1…>

/* * 泛型接口:把泛型定义在接口上 */
public interface Inter<T> { 
  public abstract void show(T t);
}

扩展集合:
原文:https://blog.csdn.net/zhangqunshuai/article/details/80660974
List , Set, Map都是接口,前两个继承至Collection接口,Map为独立接口
Set下有HashSet,LinkedHashSet,TreeSet
List下有ArrayList,Vector,LinkedList
Map下有Hashtable,LinkedHashMap,HashMap,TreeMap
集合关系图

注意:

  • Queue接口与List、Set同一级别,都是继承了Collection接口。
  • 看图你会发现,LinkedList既可以实现Queue接口,也可以实现List接口.只不过呢,
  • LinkedList实现了Queue接口。Queue接口窄化了对LinkedList的方法的访问权限(即在方法中的参数类型如果是Queue时,就完全只能访问Queue接口所定义的方法了,而不能直接访问 LinkedList的非Queue的方法),以使得只有恰当的方法才可以使用。

- Collection接口:

  • 使用Iterator(迭代器)遍历集合
    Iterator接口是Collection接口的父接口,因此Collection集合可以直接调用其方法。
    Iterator接口也是Java集合框架中的一员,与Collection系列和Map系列不同的是:
    Collection系列、Map系列集合主要是用于盛装数据对象的。 Iteration主要是用于遍历Collection中的元素。

— List 有序,可重复

ArrayList
优点: 底层数据结构是数组,查询快,增删慢。
缺点: 线程不安全,效率高
Vector
优点: 底层数据结构是数组,查询快,增删慢。
缺点: 线程安全,效率低
LinkedList
优点: 底层数据结构是链表,查询慢,增删快。
缺点: 线程不安全,效率高

—Set 无序,唯一

HashSet
底层数据结构是哈希表。(无序,唯一)
如何来保证元素唯一性?
1.依赖两个方法:hashCode()和equals()
LinkedHashSet
底层数据结构是链表和哈希表。(FIFO插入有序,唯一)
1.由链表保证元素有序
2.由哈希表保证元素唯一
TreeSet
底层数据结构是红黑树。(唯一,有序)

  1. 如何保证元素排序的呢?
    自然排序
    比较器排序
    2.如何保证元素唯一性的呢?
    根据比较的返回值是否是0来决定

Map接口

Map提供了一种映射关系,其中的元素是以键值对(key-value)的形式存储的,能够实现根据key快速查找value;
Map中的键值对以Entry类型的对象实例形式存在;
建(key值)不可重复,value值可以重复,一个value值可以和很多key值形成对应关系,每个建最多只能映射到一个值。
Map支持泛型,形式如:Map<K,V>
Map中使用put(K key,V value)方法添加
Map接口有三个比较重要的实现类,分别是HashMap、TreeMap和HashTable。
TreeMap是有序的,HashMap和HashTable是无序的。
Hashtable的方法是同步的,HashMap的方法不是同步的。这是两者最主要的区别。

JAVA集合中Comparable与Comparator区别。

Comparator在汉语中的意思是 比较器 ,Comparable在汉语中的意思是 可比的

集合中的元素在进行比较时,都会调用compareTo()方法,该方法就是Comparable接口中的定义,因此要想对集合中元素进行排序,就必须实现Comparable的接口。
代码如下:

public class Student implements Comparable<Student>{
	private String name;
	private int age;
	public Student(){
		super();
	}
	public Student (String name,int age){
		this.name=name;
		this.age=age;
	}
	public String getName(){
		return name;
	}
	public int getAge(){
		return age;
	}
	public String setName(String ename){
		this.name=ename;
		return name;
	}
	public int setAge(int ages){
		this.age=ages;
		return age;
	}
	public int compareTo(Student s){ 
		int num=this.name.length()-s.name.length();
		int num2=num==0?this.name.compareTo(s.name):num;
		int num3=num2==0?this.age-s.age:num2;
		return num3;
	}
	@Override
	public String toString() {
		return "student [name=" + name + ", age=" + age + "]";	
}
}
//测试方法
public class Test {
	public static void main(String[] args){	
		TreeSet<Student> s=new TreeSet<Student>();
		s.add(new Student("SDFGU",32));
		s.add(new Student("WRTYU",23));
		s.add(new Student("RTYUS",32));
		s.add(new Student("WETWS",23));
		s.add(new Student("SDFGU",32));
		s.add(new Student("WRTYU",33));
		s.add(new Student("QAWSER",32));
		s.add(new Student("W3ERTYUI",23));
		Iterator<Student> i=s.iterator();
		while(i.hasNext()){
			System.out.println(i.next());
		}
	}
}

Student类实现了Comparable接口中的compareTo()方法。在compareTo()方法中,首先对字符串长度进行比较,根据比较结果返回-1或1,或当长度相同时,再对name值进行比较,最后,对age进行比较。因此,可以看出学生首先按照name的长度排序,name的长度相同时会按照字母表的顺序,最后按照age排序。

  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

黎明逸

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值