Java 基础:Map的一家
0.Java中的集合框架
1.Map--接口
public interface Map<K,V>
包:java.util.Map
Map提供了一种映射关系,其中的元素是以键值对(key-value)的形式存储的,能够实现根据key快速查找value;
Map中的键值对以Entry类型的对象实例形式存在;
键(key值)不可重复,value值可以重复,一个value值可以和很多key值形成对应关系,每个建最多只能映射到一个值。
Map支持泛型,形式如:Map<K,V>
Map中使用put(K key,V value)方法添加
给定一个键和一个值,你可以将该值存储在一个Map对象. 之后,你可以通过键来访问对应的值。
当访问的值不存在的时候,方法就会抛出一个NoSuchElementException异常.
当对象的类型和Map里元素类型不兼容的时候,就会抛出一个 ClassCastException异常。
当在不允许使用Null对象的Map中使用Null对象,会抛出一个NullPointerException 异常。
当尝试修改一个只读的Map时,会抛出一个UnsupportedOperationException异常。
2.HashMap--实现类
public class HashMap<K,V> extends AbstractMap<K,V> implements Map<K,V>, Cloneable, Serializable
包:java.util.HashMap
HashMap是Map的一个重要实现类,也是最常用的,基于哈希表实现
HashMap中的Entry对象是无序排列的
Key值和value值都可以为null,但是一个HashMap只能有一个key值为null的映射(key值不可重复)
3.Hashtable--实现类
public class Hashtable<K,V> extends Dictionary<K,V> implements Map<K,V>, Cloneable, java.io.Serializable
HashTable 是以数组和单向链表结合的存储形式;
存储元素时,key通过hash映射函数得到在HashTable存储数组中的位置;
该位置存放的是hash值一致的单向链表的首元素;
新的元素存储到该位置指向的列表中;
数组存储哈希后的key,哈希值相同,则使用链表解决哈希碰撞,放到链表中。
Hashtable是遗留类,很多映射的常用功能与HashMap类似,不同的是它承自Dictionary类,并且是线程安全的,
任一时间只有一个线程能写Hashtable,并发性不如ConcurrentHashMap,因为ConcurrentHashMap引入了分段锁。
Hashtable不建议在新代码中使用,不需要线程安全的场合可以用HashMap替换,需要线程安全的场合可以用ConcurrentHashMap替换。
4.ConcurrentHashMap---实现类
public class ConcurrentHashMap<K,V> extends AbstractMap<K,V> implements ConcurrentMap<K,V>, Serializable
包:java.util.concurrent.ConcurrentHashMap
ConcurrentHashMap允许并发的读和线程安全的更新操作
在执行写操作时,ConcurrentHashMap只锁住部分的Map
并发的更新是通过内部根据并发级别将Map分割成小部分实现的
高的并发级别会造成时间和空间的浪费,低的并发级别在写线程多时会引起线程间的竞争
ConcurrentHashMap的所有操作都是线程安全
ConcurrentHashMap返回的迭代器是弱一致性,fail-safe并且不会抛出ConcurrentModificationException异常
ConcurrentHashMap不允许null的键值
可以使用ConcurrentHashMap代替HashTable,但要记住ConcurrentHashMap不会锁住整个Map
5.HashMap与Hashtable
HashTable和HashMap采用相同的存储机制,二者的实现基本一致,不同的是:
1、HashMap是非线程安全的,HashTable是线程安全的,内部的方法基本都是synchronized。
2、HashTable不允许有null值的存在。
3、因为线程安全的问题,HashMap效率比HashTable的要高。
在HashTable中调用put方法时,如果key为null,直接抛出NullPointerException。其它细微的差别还有,比如初始化Entry数组的大小等等,但基本思想和HashMap一样。
6.HashTable和ConcurrentHashMap
ConcurrentHashMap是线程安全的HashMap的实现。
同样是线程安全的类,它与HashTable在同步方面有什么不同呢?
之前我们说,synchronized关键字加锁的原理,其实是对对象加锁,不论你是在方法前加synchronized还是语句块前加,锁住的都是对象整体,
但是ConcurrentHashMap的同步机制和这个不同,它不是加synchronized关键字,而是基于lock操作的,
这样的目的是保证同步的时候,锁住的不是整个对象。
事实上,ConcurrentHashMap可以满足concurrentLevel个线程并发无阻塞的操作集合对象。
ConcurrentHashMap基于concurrentLevel划分出了多个Segment来对key-value进行存储,从而避免每次锁定整个数组,在默认的情况下,允许16个线程并发无阻塞的操作集合对象,尽可能地减少并发时的阻塞现象。
在多线程的环境中,相对于HashTable,ConcurrentHashMap会带来很大的性能提升!
部分内容参考:http://www.cnblogs.com/wang-meng/p/5808006.html