public class BTreeMap<K,V> extends java.util.AbstractMap<K,V> implements java.util.concurrent.ConcurrentNavigableMap<K,V>, Bind.MapWithModificationListener<K,V>
ConcurrentNavigableMap implementation.
The map is sorted according to the natural
ordering of its keys, or by a Comparator provided at map
creation time.
Insertion, removal,
update, and access operations safely execute concurrently by
multiple threads. Iterators are weakly consistent, returning
elements reflecting the state of the map at some point at or since
the creation of the iterator. They do not throw ConcurrentModificationException, and may proceed concurrently with
other operations. Ascending key ordered views and their iterators
are faster than descending ones.
It is possible to obtain consistent iterator by using snapshot()
method.
All Map.Entry pairs returned by methods in this class
and its views represent snapshots of mappings at the time they were
produced. They do not support the Entry.setValue
method. (Note however that it is possible to change mappings in the
associated map using put, putIfAbsent, or
replace, depending on exactly which effect you need.)
This collection has optional size counter. If this is enabled Map size is
kept in Atomic.Long variable. Keeping counter brings considerable
overhead on inserts and removals.
If the size counter is not enabled the size method is not a constant-time operation.
Determining the current number of elements requires a traversal of the elements.
Additionally, the bulk operations putAll, equals, and
clear are not guaranteed to be performed
atomically. For example, an iterator operating concurrently with a
putAll operation might view only some of the added
elements. NOTE: there is an optional
This class and its views and iterators implement all of the
optional methods of the Map and Iterator
interfaces. Like most other concurrent collections, this class does
not permit the use of null keys or values because some
null return values cannot be reliably distinguished from the absence of
elements.
Theoretical design of BTreeMap is based on paper
from Philip L. Lehman and S. Bing Yao. More practical aspects of BTreeMap implementation are based on notes
and demo application from Thomas Dinsdale-Young.
B-Linked-Tree used here does not require locking for read. Updates and inserts locks only one, two or three nodes.
This B-Linked-Tree structure does not support removal well, entry deletion does not collapse tree nodes. Massive
deletion causes empty nodes and performance lost. There is workaround in form of compaction process, but it is not
implemented yet.| Modifier and Type | Class and Description |
|---|---|
protected static interface |
BTreeMap.BNode
common interface for BTree node
|
(package private) static class |
BTreeMap.BTreeEntryIterator<K,V> |
protected static class |
BTreeMap.BTreeIterator |
(package private) static class |
BTreeMap.BTreeKeyIterator<K> |
(package private) static class |
BTreeMap.BTreeValueIterator<V> |
protected static class |
BTreeMap.DescendingMap<K,V> |
protected static class |
BTreeMap.DirNode |
(package private) static class |
BTreeMap.EntrySet<K1,V1> |
static class |
BTreeMap.KeySet<E> |
protected static class |
BTreeMap.LeafNode |
protected static class |
BTreeMap.NodeSerializer<A,B> |
protected static class |
BTreeMap.SubMap<K,V> |
protected static class |
BTreeMap.ValRef
if
valsOutsideNodes is true, this class is used instead of values. |
(package private) static class |
BTreeMap.Values<E> |
| Modifier and Type | Field and Description |
|---|---|
protected static int |
B_TREE_NODE_DIR_C |
protected static int |
B_TREE_NODE_DIR_L |
protected static int |
B_TREE_NODE_DIR_LR |
protected static int |
B_TREE_NODE_DIR_R |
protected static int |
B_TREE_NODE_LEAF_C |
protected static int |
B_TREE_NODE_LEAF_L |
protected static int |
B_TREE_NODE_LEAF_LR |
protected static int |
B_TREE_NODE_LEAF_R |
static java.util.Comparator |
COMPARABLE_COMPARATOR |
protected java.util.Comparator |
comparator
keys are sorted by this
|
protected Atomic.Long |
counter |
private java.util.concurrent.ConcurrentNavigableMap<K,V> |
descendingMap |
protected static java.lang.Object |
EMPTY |
protected Engine |
engine
DB Engine in which entries are persisted
|
private BTreeMap.EntrySet |
entrySet |
protected boolean |
hasValues
is this a Map or Set? if false, entries do not have values, only keys are allowed
|
protected BTreeKeySerializer |
keySerializer
Serializer used to convert keys from/into binary form.
|
private BTreeMap.KeySet |
keySet |
protected java.util.List<java.lang.Long> |
leftEdges |
protected int |
maxNodeSize
maximal node size allowed in this BTree
|
protected Bind.MapListener<K,V>[] |
modListeners |
protected java.lang.Object |
modListenersLock |
protected LongConcurrentHashMap<java.lang.Long> |
nodeLocks
holds node level locks
|
protected Serializer<BTreeMap.BNode> |
nodeSerializer |
protected int |
numberOfNodeMetas |
protected long |
rootRecidRef
recid under which reference to rootRecid is stored
|
protected boolean |
valsOutsideNodes
store values as part of BTree nodes
|
private BTreeMap.Values |
values |
protected Serializer<V> |
valueSerializer
Serializer used to convert keys from/into binary form
|
| Constructor and Description |
|---|
BTreeMap(Engine engine,
long rootRecidRef,
int maxNodeSize,
boolean valsOutsideNodes,
long counterRecid,
BTreeKeySerializer<K> keySerializer,
Serializer<V> valueSerializer,
java.util.Comparator<K> comparator,
int numberOfNodeMetas,
boolean disableLocks)
Constructor used to create new BTreeMap.
|
| Modifier and Type | Method and Description |
|---|---|
protected static long[] |
arrayLongPut(long[] array,
int pos,
long value) |
protected static java.lang.Object[] |
arrayPut(java.lang.Object[] array,
int pos,
java.lang.Object value)
expand array size by 1, and put value at given position.
|
protected static void |
assertNoLocks(LongConcurrentHashMap<java.lang.Long> locks) |
java.util.Map.Entry<K,V> |
ceilingEntry(K key) |
K |
ceilingKey(K key) |
void |
clear() |
void |
close()
Closes underlying storage and releases all resources.
|
java.util.Comparator<? super K> |
comparator() |
boolean |
containsKey(java.lang.Object key) |
boolean |
containsValue(java.lang.Object value) |
protected static long |
createRootRef(Engine engine,
BTreeKeySerializer keySer,
Serializer valueSer,
java.util.Comparator comparator,
int numberOfNodeMetas)
creates empty root node and returns recid of its reference
|
java.util.NavigableSet<K> |
descendingKeySet() |
java.util.concurrent.ConcurrentNavigableMap<K,V> |
descendingMap() |
(package private) java.util.Iterator<java.util.Map.Entry<K,V>> |
entryIterator() |
java.util.Set<java.util.Map.Entry<K,V>> |
entrySet() |
protected int |
findChildren(java.lang.Object key,
java.lang.Object[] keys)
Find the first children node with a key equal or greater than the given key.
|
protected java.util.Map.Entry<K,V> |
findLarger(K key,
boolean inclusive) |
protected Fun.Tuple2<java.lang.Integer,BTreeMap.LeafNode> |
findLargerNode(K key,
boolean inclusive) |
protected java.util.Map.Entry<K,V> |
findSmaller(K key,
boolean inclusive) |
private java.util.Map.Entry<K,V> |
findSmallerRecur(BTreeMap.BNode n,
K key,
boolean inclusive) |
java.util.Map.Entry<K,V> |
firstEntry() |
K |
firstKey() |
java.util.Map.Entry<K,V> |
floorEntry(K key) |
K |
floorKey(K key) |
V |
get(java.lang.Object key) |
protected java.lang.Object |
get(java.lang.Object key,
boolean expandValue) |
Engine |
getEngine() |
java.util.concurrent.ConcurrentNavigableMap<K,V> |
headMap(K toKey) |
java.util.concurrent.ConcurrentNavigableMap<K,V> |
headMap(K toKey,
boolean inclusive) |
java.util.Map.Entry<K,V> |
higherEntry(K key) |
K |
higherKey(K key) |
boolean |
isEmpty() |
(package private) java.util.Iterator<K> |
keyIterator() |
java.util.NavigableSet<K> |
keySet() |
java.util.Map.Entry<K,V> |
lastEntry() |
private java.util.Map.Entry<K,V> |
lastEntryRecur(BTreeMap.BNode n) |
K |
lastKey() |
protected static void |
lock(LongConcurrentHashMap<java.lang.Long> locks,
long recid) |
java.util.Map.Entry<K,V> |
lowerEntry(K key) |
K |
lowerKey(K key) |
protected java.util.Map.Entry<K,V> |
makeEntry(java.lang.Object key,
java.lang.Object value) |
void |
modificationListenerAdd(Bind.MapListener<K,V> listener)
Add new modification listener notified when Map has been updated
|
void |
modificationListenerRemove(Bind.MapListener<K,V> listener)
Remove registered notification listener
|
java.util.NavigableSet<K> |
navigableKeySet() |
protected long |
nextDir(BTreeMap.DirNode d,
java.lang.Object key) |
protected void |
notify(K key,
V oldValue,
V newValue) |
java.util.Map.Entry<K,V> |
pollFirstEntry() |
java.util.Map.Entry<K,V> |
pollLastEntry() |
protected static java.util.SortedMap<java.lang.String,java.lang.Object> |
preinitCatalog(DB db)
hack used for DB Catalog
|
private static void |
printRecur(BTreeMap m,
long recid,
java.lang.String s) |
void |
printTreeStructure() |
V |
put(K key,
V value) |
protected V |
put2(K key,
V value2,
boolean putOnlyIfAbsent) |
V |
putIfAbsent(K key,
V value) |
V |
remove(java.lang.Object key) |
boolean |
remove(java.lang.Object key,
java.lang.Object value) |
private V |
remove2(java.lang.Object key,
java.lang.Object value) |
V |
replace(K key,
V value) |
boolean |
replace(K key,
V oldValue,
V newValue) |
int |
size() |
long |
sizeLong() |
java.util.NavigableMap<K,V> |
snapshot()
Make readonly snapshot view of current Map.
|
java.util.concurrent.ConcurrentNavigableMap<K,V> |
subMap(K fromKey,
boolean fromInclusive,
K toKey,
boolean toInclusive) |
java.util.concurrent.ConcurrentNavigableMap<K,V> |
subMap(K fromKey,
K toKey) |
java.util.concurrent.ConcurrentNavigableMap<K,V> |
tailMap(K fromKey) |
java.util.concurrent.ConcurrentNavigableMap<K,V> |
tailMap(K fromKey,
boolean inclusive) |
(package private) static <E> java.util.List<E> |
toList(java.util.Collection<E> c) |
protected static void |
unlock(LongConcurrentHashMap<java.lang.Long> locks,
long recid) |
protected static void |
unlockAll(LongConcurrentHashMap<java.lang.Long> locks) |
protected V |
valExpand(java.lang.Object ret) |
(package private) java.util.Iterator<V> |
valueIterator() |
java.util.Collection<V> |
values() |
finalize, getClass, notify, notifyAll, wait, wait, waitpublic static final java.util.Comparator COMPARABLE_COMPARATOR
protected static final java.lang.Object EMPTY
protected static final int B_TREE_NODE_LEAF_LR
protected static final int B_TREE_NODE_LEAF_L
protected static final int B_TREE_NODE_LEAF_R
protected static final int B_TREE_NODE_LEAF_C
protected static final int B_TREE_NODE_DIR_LR
protected static final int B_TREE_NODE_DIR_L
protected static final int B_TREE_NODE_DIR_R
protected static final int B_TREE_NODE_DIR_C
protected final long rootRecidRef
protected final BTreeKeySerializer keySerializer
protected final Serializer<V> valueSerializer
protected final java.util.Comparator comparator
protected final LongConcurrentHashMap<java.lang.Long> nodeLocks
protected final int maxNodeSize
protected final Engine engine
protected final boolean hasValues
protected final boolean valsOutsideNodes
protected final java.util.List<java.lang.Long> leftEdges
private final BTreeMap.KeySet keySet
private final BTreeMap.EntrySet entrySet
private final BTreeMap.Values values
protected final Atomic.Long counter
protected final int numberOfNodeMetas
protected final Serializer<BTreeMap.BNode> nodeSerializer
protected final java.lang.Object modListenersLock
protected Bind.MapListener<K,V>[] modListeners
public BTreeMap(Engine engine, long rootRecidRef, int maxNodeSize, boolean valsOutsideNodes, long counterRecid, BTreeKeySerializer<K> keySerializer, Serializer<V> valueSerializer, java.util.Comparator<K> comparator, int numberOfNodeMetas, boolean disableLocks)
engine - used for persistencerootRecidRef - reference to root recidmaxNodeSize - maximal BTree Node size. Node will split if number of entries is highervalsOutsideNodes - Store Values outside of BTree Nodes in separate record?counterRecid - recid under which `Atomic.Long` is stored, or `0` for no counterkeySerializer - Serializer used for keys. May be null for default value.valueSerializer - Serializer used for values. May be null for default valuecomparator - Comparator to sort keys in this BTree, may be null.numberOfNodeMetas - number of meta records associated with each BTree nodedisableLocks - makes class thread-unsafe but bit fasterprotected static java.util.SortedMap<java.lang.String,java.lang.Object> preinitCatalog(DB db)
protected static long createRootRef(Engine engine, BTreeKeySerializer keySer, Serializer valueSer, java.util.Comparator comparator, int numberOfNodeMetas)
protected final int findChildren(java.lang.Object key,
java.lang.Object[] keys)
public V get(java.lang.Object key)
protected java.lang.Object get(java.lang.Object key,
boolean expandValue)
protected V valExpand(java.lang.Object ret)
protected long nextDir(BTreeMap.DirNode d, java.lang.Object key)
public V remove(java.lang.Object key)
private V remove2(java.lang.Object key, java.lang.Object value)
public void clear()
protected java.util.Map.Entry<K,V> makeEntry(java.lang.Object key, java.lang.Object value)
public boolean isEmpty()
public int size()
public long sizeLong()
sizeLong in interface Bind.MapWithModificationListener<K,V>public boolean remove(java.lang.Object key,
java.lang.Object value)
public java.util.Comparator<? super K> comparator()
private java.util.Map.Entry<K,V> findSmallerRecur(BTreeMap.BNode n, K key, boolean inclusive)
private java.util.Map.Entry<K,V> lastEntryRecur(BTreeMap.BNode n)
protected Fun.Tuple2<java.lang.Integer,BTreeMap.LeafNode> findLargerNode(K key, boolean inclusive)
public boolean containsKey(java.lang.Object key)
public boolean containsValue(java.lang.Object value)
public java.util.concurrent.ConcurrentNavigableMap<K,V> subMap(K fromKey, boolean fromInclusive, K toKey, boolean toInclusive)
public java.util.concurrent.ConcurrentNavigableMap<K,V> tailMap(K fromKey, boolean inclusive)
java.util.Iterator<K> keyIterator()
java.util.Iterator<V> valueIterator()
public java.util.NavigableSet<K> keySet()
public java.util.NavigableSet<K> navigableKeySet()
public java.util.Collection<V> values()
public java.util.NavigableSet<K> descendingKeySet()
static <E> java.util.List<E> toList(java.util.Collection<E> c)
public java.util.NavigableMap<K,V> snapshot()
public void modificationListenerAdd(Bind.MapListener<K,V> listener)
Bind.MapWithModificationListenermodificationListenerAdd in interface Bind.MapWithModificationListener<K,V>listener - callback interface notified when map changespublic void modificationListenerRemove(Bind.MapListener<K,V> listener)
Bind.MapWithModificationListenermodificationListenerRemove in interface Bind.MapWithModificationListener<K,V>listener - callback interface notified when map changespublic void close()
public Engine getEngine()
public void printTreeStructure()
private static void printRecur(BTreeMap m, long recid, java.lang.String s)
protected static long[] arrayLongPut(long[] array,
int pos,
long value)
protected static java.lang.Object[] arrayPut(java.lang.Object[] array,
int pos,
java.lang.Object value)
protected static void assertNoLocks(LongConcurrentHashMap<java.lang.Long> locks)
protected static void unlock(LongConcurrentHashMap<java.lang.Long> locks, long recid)
protected static void unlockAll(LongConcurrentHashMap<java.lang.Long> locks)
protected static void lock(LongConcurrentHashMap<java.lang.Long> locks, long recid)