【主要内容】
java collection 下面常用的三大接口
Map接口图谱
hashMap、HashTable、LinkedHashMap、TreeMap
【补充点】:
java向上向下转型
- java collection 下面常用的三大接口:
list 存储有序,不一定唯一
set 存储无序,没有重复(唯一)
map 存储key-value对 key不可以重复
- Map接口图谱:
(图片转自https://www.cnblogs.com/LeslieXia/p/5788816.html)
虚线 extends
实现implements
常用的类:HashMap、HashTable、LinkedHashMap、TreeMap
- hashMap
有序:需要计算hashcode 确定自己的位置, node的key的hashcode 和 node的value的hashcode按位异或
运用实例:
package chap9_Collection.map;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
public class Test1_hashmap {
public static void main(String[] args) {
HashMap hashMap = new HashMap();
hashMap.put(null, 1);
hashMap.put(null, 2);// null==null 所以只会保留最新更新的
hashMap.put("zibo", "ziyan");
hashMap.put("zhangzibo", "rontziyan");
hashMap.put(2, "2");
hashMap.put(3, "3");
System.out.println(hashMap);
System.out.println(hashMap.keySet());
System.out.println(hashMap.get("zhangzibo"));
System.out.println("is 2 a key :" + hashMap.containsKey(2));
System.out.println("is 2 a value :" + hashMap.containsValue(2));
System.out.println("is 'zhangzibo' a key :" + hashMap.containsKey("zhangzibo"));
// 1.迭代遍历entrySet()
System.out.println(hashMap.entrySet());
Iterator iterator = hashMap.entrySet().iterator();
while (iterator.hasNext()) {
Map.Entry entry = (Map.Entry) iterator.next();
System.out.println(entry.getKey() + "-->" + entry.getValue());
}
// 2.foreach遍历
for (Object object : hashMap.entrySet()) {
// for(Map.Entry<Object,Object> entry: hashMap.entrySet()) {
//
// }
// 如果不清楚类型的话,都用object接
Map.Entry<Object, Object> entry = (Map.Entry<Object, Object>) object;
System.out.println(entry.getKey() + "-->" + entry.getValue());
}
// 3. 对象的foreach lambda表达式 (推荐使用)
hashMap.forEach((key, value) -> {
System.out.println(key + "-->" + value);
});
// 4 ()单纯遍历key或者value:
for (Object object : hashMap.keySet()) {
System.out.println(object);
}
for (Object object : hashMap.values())
System.out.println(object);
}
}
问题:
for(Map.Entry<Object,Object> entry: hashMap.entrySet())
编译不通过,可能的解释原因,entrySet都是非rough的set类型,带有泛型参数,由于编译时候的泛型擦除性,保证安全的情况下不会编译通过。结局方法都是先用大的承接,在向下转型
-
红黑树
-
hashMap底层实现
-
linkedhashmap
继承hashMap,内部维护一个双向链表 -
treemap
是一个有序的key-value集合,底层是红黑树
extends AbstractMap
implement NavigableMap Cloneable Serialzable
有序体现在:红黑树的自己排序,或者创建映射的时候提供的Comparator进行排序
iterator + failfast
https://www.jianshu.com/p/1c2d31b1f69e
java中迭代器提供统一的接口
所有对数据结构的操作:add remove clear ensureCaacity等操作都会让这个数据结构的modCount++,在获取迭代器的时候,数据结构会把这个成员变量交给迭代器的expectedModCount,因此在迭代的过程中只要不出现改变数据结构,都不会发生快速失败机制。如果在迭代的过程中,发生了add,就会让modCountexpectedModCount不相等,最终会抛出ConcurrentModificationException
- hashtable
【补充】
上下转型(上-父,下-子)
向上
Father a=new Son() 相当于是一个小的 具体的 放到一个大的容器里面,当然是可以的
动态绑定(重写):父类的方法如果被重写,a调用的是子类的方法
a不能调用子类独有的方法(如果非要调用子类的方法,一般做法是使用向下转型)
向下:需要强转
除非本身是向上转型过来的转回去不用进行判断
其他的最好先instanceOf(目标类型)
为什么需要上转之后下转呢
前面hashset例子中:泛型的擦除不能直接获取
另外:当一个函数参数采用父类的时候,可以根据传入的子类,执行子类对应该名称的方法
//Son1 Son2 都继承Father
public static func(Father father){...}
func(new Son1());//执行Son1对应的func方法
func(new Son2());//执行Son2对应的func方法