集合框架和泛型(二)map、泛型、Collections
java常用集合关系简图
Map(键值对、键唯一、值不唯一)
Map集合中存储的是键值对,键不能重复,值可以重复。根据键得到值,对map集合遍历时先得到键的set集合,对set集合进行遍历,得到相应的值。
HashMap
数组方式存储key/value,线程非安全,允许null作为key和value,key不可以重复,value允许重复,不保证元素迭代顺序是按照插入时的顺序,key的hash值是先计算key的hashcode值,然后再进行计算,每次容量扩容会重新计算所以key的hash值,会消耗资源,要求key必须重写equals和hashcode方法
默认初始容量16,加载因子0.75,扩容为旧容量乘2,查找元素快,如果key一样则比较value,如果value不一样,则按照链表结构存储value,就是一个key后面有多个value;
方法
1、添加:
V put(K key, V value) (可以相同的key值,但是添加的value值会覆盖前面的,返回值是前一个,如果没有就返回null)
putAll(Map<? extends K,? extends V> m) 从指定映射中将所有映射关系复制到此映射中(可选操作)。
2、删除
remove() 删除关联对象,指定key对象
clear() 清空集合对象
3、获取
value get(key) 可以用于判断键是否存在的情况。当指定的键不存在的时候,返回的是null。
4、判断:
boolean isEmpty() 长度为0返回true否则false
boolean containsKey(Object key) 判断集合中是否包含指定的key
boolean containsValue(Object value) 判断集合中是否包含指定的value
4、长度:
Int size()
map的主要的方法就这几个
遍历方法
第一种:KeySet()
将Map中所有的键存入到set集合中。因为set具备迭代器。所有可以迭代方式取出所有的键,再根据get方法。获取每一个键对应的值。 keySet():迭代后只能通过get()取key 。
取到的结果会乱序,是因为取得数据行主键的时候,使用了HashMap.keySet()方法,而这个方法返回的Set结果,里面的数据是乱序排放的。
第二种: values() 获取所有的值.
Collection values()不能获取到key对象
第三种:entrySet()
Set<Map.Entry<K,V>> entrySet() //返回此映射中包含的映射关系的 Set 视图。(一个关系就是一个键-值对),就是把(key-value)作为一个整体一对一对地存放到Set集合当中的。Map.Entry表示映射关系。entrySet():迭代后可以e.getKey(),e.getValue()两种方法来取key和value。返回的是Entry接口。
示例
public class MapTest {
public static void main(String[] args) {
Map<String,String> maps=new HashMap<String,String>();
maps.put("1","test1"); //向Map集合中存储键值对
maps.put("2","test2");
maps.put("3","test3");
maps.put("4","test4");
maps.put("5","test5");
System.out.println("key值为:1的用户"+maps.get("1"));//通过key获取值
//通过key删除键值对
maps.remove("1");
//maps中的键值对个数
System.out.println(maps.size());
System.out.println(maps.containsKey("1"));//判断该Key在集合中是否存在
//containsValue:判断值是否存在
System.out.println("-----------------");
//1:仅遍历key
Set<String> keySet = maps.keySet();
for (String object : keySet) {
System.out.println("集合中的key:"+object);
}
System.out.println("-----------------");
//2:仅遍历value
Collection<String> values = maps.values();
for(String item:values){
System.out.println("集合中的value:"+item);
}
System.out.println("-----------------");
//3:key和value同时遍历 Entry:
Set<Entry<String,String>> entrySet = maps.entrySet();
for (Entry<String,String> entry : entrySet) {
System.out.println("key:"+entry.getKey()+",Value:"+entry.getValue());
}
}
}
输出结果
key值为:1的用户test1
4
false
-----------------
集合中的key:3
集合中的key:2
集合中的key:5
集合中的key:4
-----------------
集合中的value:test3
集合中的value:test2
集合中的value:test5
集合中的value:test4
-----------------
key:3,Value:test3
key:2,Value:test2
key:5,Value:test5
key:4,Value:test4
泛型
泛型有三种使用方式,分别为:泛型类、泛型接口、泛型方法
泛型类型用于类的定义中,被称为泛型类。通过泛型可以完成对一组类的操作对外开放相同的接口。最典型的就是各种容器类,如:List、Set、Map。
泛型类
class 类名称 <泛型标识:可以随便写任意标识号,标识指定的泛型的类型>{
private 泛型标识 /*(成员变量类型)*/ var;
.....
}
}
//此处T可以随便写为任意标识,常见的如T、E、K、V等形式的参数常用于表示泛型
//在实例化泛型类时,必须指定T的具体类型
public class Generic<T>{
//key这个成员变量的类型为T,T的类型由外部指定
private T key;
public Generic(T key) { //泛型构造方法形参key的类型也为T,T的类型由外部指定
this.key = key;
}
public T getKey(){ //泛型方法getKey的返回值类型为T,T的类型由外部指定
return key;
}
}
泛型方法
public class genericUtils<E>{
public <T>T getSomething(){
System.out.println("泛型方法");
return null;
}
public <T>String doSomething(T t){
return "";
}
public <T>T doSome(T t ){
System.out.println(t);
return t;
}
}