您的位置:首页 > 编程语言 > Java开发

jdk 源码分析(5)java ConcurrentSkipListMap结构

2017-08-02 21:02 411 查看
理解ConcurrentSkipListMap 只需要理解存储方式就行了



跳表结构之下往上分层,比如需要找117,首先会判断最高层,先比较21,在比较37 ,再比较37左边的,因为左边结束了,所以只能往下走,一直找到目标为止:

寻找规则,从最高层开始,先右,再下,直到最后。

1)单个节点定义:链式。

static final class Node<K,V> {
final K key;
volatile Object value;
volatile Node<K,V> next;

/**
* Creates a new regular node.
*/
Node(K key, Object value, Node<K,V> next) {
this.key = key;
this.value = value;
this.next = next;
}


2)单个节点,主要增加对right和down的指引

static class Index<K,V> {
final Node<K,V> node;
final Index<K,V> down;
volatile Index<K,V> right;

/**
* Creates index node with given values.
*/
Index(Node<K,V> node, Index<K,V> down, Index<K,V> right) {
this.node = node;
this.down = down;
this.right = right;
}


3)再次包装,产生对leve的定义。

static final class HeadIndex<K,V> extends Index<K,V> {
final int level;
HeadIndex(Node<K,V> node, Index<K,V> down, Index<K,V> right, int level) {
super(node, down, right);
this.level = level;
}
}


如果对数据结构了解,上面headIndex 就可以构成跳表。

put的时候查找位置:

private Node<K,V> findPredecessor(Object key, Comparator<? super K> cmp) {

if (key == null)

throw new NullPointerException(); // don't postpone errors

for (;;) {//先找right

for (Index<K,V> q = head, r = q.right, d;;) {

if (r != null) {

Node<K,V> n = r.node;

K k = n.key;

if (n.value == null) {

if (!q.unlink(r))

break;           // restart

r = q.right;         // reread r

continue;

}

if (cpr(cmp, key, k) > 0) {

q = r;

r = r.right;

continue;

}

}

//再找down
if ((d = q.down) == null)

return q.node;

q = d;

r = d.right;

}

}


可以看到都是先右边再下边。

不过这里的跳表有点不同,每个节点不是一个单点,而是一个链表。通过next 连接。

for (Node<K,V> b = findPredecessor(key, cmp), n = b.next;;) {

if (n != null) {

Object v; int c;

Node<K,V> f = n.next;

if (n != b.next)               // inconsistent read

break;

if ((v = n.value) == null) {   // n is deleted

n.helpDelete(b, f);

break;

}

if (b.value == null || v == n) // b is deleted

break;

if ((c = cpr(cmp, key, n.key)) > 0) {

b = n;

n = f;

continue;

}

if (c == 0) {

if (onlyIfAbsent || n.casValue(v, value)) {

@SuppressWarnings("unchecked") V vv = (V)v;

return vv;

    }

break; // restart if lost race to replace value

}

// else c < 0; fall through

}


z = new Node<K,V>(key, value, n);

if (!b.casNext(n, z))

break;         // restart if lost race to append to b

break outer;

}

}


里面还有// find insertion points and splice in

数据的level配置,已经插入新的节点。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  源代码 jdk