searchusermenu
  • 发布文章
  • 消息中心
点赞
收藏
评论
分享
原创

使用CAS实现无锁队列

2024-08-02 09:34:17
3
0
在Java中,实现lock-free(无锁)数据结构通常依赖于CAS(Compare-And-Swap)原语。CAS是一种原子操作,用于比较内存中的值是否等于预期值,如果相等则将其更新为新值,否则不做任何操作。这种机制可以避免传统的锁机制,提高并发性能和系统吞吐量。

### 无锁队列的实现

#### 1. 节点类(Node)

节点类包含值和指向下一个节点的引用。
public class Node {
    Integer value;
    AtomicReference<Node> next;

    public Node(Integer value) {
        this.value = value;
        this.next = new AtomicReference<>(null);
    }
}
#### 2. 链表类(LockFreeQueue)

使用`AtomicReference`来实现链表的CAS操作。链表头节点是一个哨兵节点,用于简化插入和删除操作。

import java.util.concurrent.atomic.AtomicReference;

public class LockFreeQueue {
private final AtomicReference<node> head = new AtomicReference<>(null);

public void enqueue(Integer value) {
    Node newNode = new Node(value);
    while (true) {
        Node cureentHeadNode = head.get();
        newNode.next = new AtomicReference<>(cureentHeadNode);
        if (head.compareAndSet(cureentHeadNode, newNode)) {
            break;
        }
    }
}

public Integer dequeue() {
    while (true) {
        Node currentHeadNode = head.get();
        if (currentHeadNode == null) {
            return null;
        }
        Integer value = currentHeadNode.value;
        Node nextNode = currentHeadNode.next.get();
        if (head.compareAndSet(currentHeadNode, nextNode)) {
            return value;
        }
    }
}

public boolean isEmpty() {
    return head.get() == null;
}

public static void main(String[] args) throws Exception {
    LockFreeFILOQueue queue = new LockFreeFILOQueue();
    Thread[] threads = new Thread[10];
    for (int i = 0; i < threads.length; i++) {
        int finalI = i;
        Thread thread = new Thread(() -> queue.enqueue(finalI));
        threads[i] = thread;
        thread.start();
    }
    
    System.out.print("[");
    boolean first = true;
    while (!queue.isEmpty()){
           if(first){
               first=false;
           }else{
               System.out.print(",");
           }
           System.out.print(queue.dequeue());
    }
    System.out.println("]");
}

}

### 解析:

* **节点类**:`Node` 类包含整数值和指向下一个节点的引用。
* **链表类**:
    * **头节点**:`head` 使用 `AtomicReference` 实现,始终指向哨兵节点。
    * **入队操作**:使用 `compareAndSet` 方法将新节点插入链表中,确保操作的原子性。
    * **出队操作**:使用 `compareAndSet` 删除头节点,确保操作的原子性。

### 总结

使用CAS实现的无锁队列具有高并发性能,避免了传统锁机制的开销和死锁问题。上述示例展示了如何在Java中使用CAS实现一个简单的无锁队列。你可以根据具体需求扩展和优化数据结构的实现。


0条评论
作者已关闭评论
l****n
6文章数
0粉丝数
l****n
6 文章 | 0 粉丝
原创

使用CAS实现无锁队列

2024-08-02 09:34:17
3
0
在Java中,实现lock-free(无锁)数据结构通常依赖于CAS(Compare-And-Swap)原语。CAS是一种原子操作,用于比较内存中的值是否等于预期值,如果相等则将其更新为新值,否则不做任何操作。这种机制可以避免传统的锁机制,提高并发性能和系统吞吐量。

### 无锁队列的实现

#### 1. 节点类(Node)

节点类包含值和指向下一个节点的引用。
public class Node {
    Integer value;
    AtomicReference<Node> next;

    public Node(Integer value) {
        this.value = value;
        this.next = new AtomicReference<>(null);
    }
}
#### 2. 链表类(LockFreeQueue)

使用`AtomicReference`来实现链表的CAS操作。链表头节点是一个哨兵节点,用于简化插入和删除操作。

import java.util.concurrent.atomic.AtomicReference;

public class LockFreeQueue {
private final AtomicReference<node> head = new AtomicReference<>(null);

public void enqueue(Integer value) {
    Node newNode = new Node(value);
    while (true) {
        Node cureentHeadNode = head.get();
        newNode.next = new AtomicReference<>(cureentHeadNode);
        if (head.compareAndSet(cureentHeadNode, newNode)) {
            break;
        }
    }
}

public Integer dequeue() {
    while (true) {
        Node currentHeadNode = head.get();
        if (currentHeadNode == null) {
            return null;
        }
        Integer value = currentHeadNode.value;
        Node nextNode = currentHeadNode.next.get();
        if (head.compareAndSet(currentHeadNode, nextNode)) {
            return value;
        }
    }
}

public boolean isEmpty() {
    return head.get() == null;
}

public static void main(String[] args) throws Exception {
    LockFreeFILOQueue queue = new LockFreeFILOQueue();
    Thread[] threads = new Thread[10];
    for (int i = 0; i < threads.length; i++) {
        int finalI = i;
        Thread thread = new Thread(() -> queue.enqueue(finalI));
        threads[i] = thread;
        thread.start();
    }
    
    System.out.print("[");
    boolean first = true;
    while (!queue.isEmpty()){
           if(first){
               first=false;
           }else{
               System.out.print(",");
           }
           System.out.print(queue.dequeue());
    }
    System.out.println("]");
}

}

### 解析:

* **节点类**:`Node` 类包含整数值和指向下一个节点的引用。
* **链表类**:
    * **头节点**:`head` 使用 `AtomicReference` 实现,始终指向哨兵节点。
    * **入队操作**:使用 `compareAndSet` 方法将新节点插入链表中,确保操作的原子性。
    * **出队操作**:使用 `compareAndSet` 删除头节点,确保操作的原子性。

### 总结

使用CAS实现的无锁队列具有高并发性能,避免了传统锁机制的开销和死锁问题。上述示例展示了如何在Java中使用CAS实现一个简单的无锁队列。你可以根据具体需求扩展和优化数据结构的实现。


文章来自个人专栏
微服务1
6 文章 | 1 订阅
0条评论
作者已关闭评论
作者已关闭评论
0
0