Art of Multiprocessor Programming 答案 ch9

本文探讨了多核环境下无锁数据结构的实现细节,特别是add、remove和contains方法。通过分析锁的获取顺序避免死锁,确保线程安全。在特定并发场景下,如线程A尝试移除节点B,而线程B在A与B之间插入节点,文章解释了如何处理这些复杂情况,保证操作的正确性和线性化点。同时,证明了在无锁数据结构中,如果前驱节点可达,则一定能到达尾节点。
摘要由CSDN通过智能技术生成

100.   将add()方法的 if(cur.key == key) return false去掉,改为找到 pred.key <= key && curr.key > key为插入的位置。remove()方法和contains()方法都是找到任意一个key == key时结束。

101. 所有的锁都按照升序获得,不会有循环,所以无死锁。

102. 当线程拥有pred.lock和curr.lock的时候,与这2个节点无关的操作并行操作,结果与这个add()方法无关,可以在串行化的历史中任意安排这2个操作的顺序;同时与这2个节点相关的操作,包括在pred后插入节点,删除pred和删除curr都将在获得2个锁的时候串行执行。这是add方法的可线性化点。

103. 没有对获得锁的循环。

104. 只要有pred和curr的关系不断变化就可以。比如说当前节点  head--> ... --> A --> B--> ... --> tail ; Threada想要remove B, Threadb不断在AB之间插入节点:

Ta.pred = A, Ta.curr = B; ==> Tb.pred = A, Tb.curr = B; Tb.pred.lock(), Tb.curr.lock(); ==> Tb inserts A1 ==> A-->A1-->B 

==> Ta.pred.lock(), Ta.curr.lock() ==> Ta.validate ==> Ta.pred.next (A.next) != Ta.curr (B) ==> Ta tries remove again.

==> Tb inserts A2 ==> Ta failed ==> ...

或者重复的插入和删除:

Ta.pred = A, Ta.curr = B ==> Tb.pred = A, Tb.curr = B; Tb.pred.lock(), Tb.curr.lock() ==> Tb inserts A1 ==> A-->A1-->B

==> Ta.pred.lock(), Ta.curr.lock() ==> Ta.validate ==> Ta.pred.next != Ta.curr ==> Ta tries remove again.

==> Ta.pred = A1, Ta.curr = B; Tb.pred = A, Tb.curr = A1; Tb.pred.lock, Tb.curr.lock; ==> Tb.remove(curr) ==> A-->B

==> Ta.pred.lock, Ta.curr.lock ==> Ta.validate ==> Ta.pred not reachable ==> Ta tries remove again

==> Repeat

105.

  public boolean contains(T item) {
    Node last = null, pred = null, curr = null;
    int key = item.hashCode();
    head.lock();
    try {
      pred = head;
      curr = pred.next;
      curr.lock();
      try {
        while (curr.key < key) {
          pred.unlock();
          pred = curr;
          curr = curr.next;
          curr.lock();
        }
        return (curr.key == key);
      } finally {
        curr.unlock();
      }
    } finally 
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值