高手好,这几天研究AbstractQueuedSynchronizer 底层遇到一个问题,如图 上面有个一个关于 enq进入队列问题然后自己想画一下这个双向链表可是不知道如何画 因为head与t是同一个对象 然后tail 与 node同一个对象 不知道该怎么画,请高手帮忙看下 在此谢过
业精于勤,荒于嬉;行成于思,毁于随。
@dj鄭豆漿 不知道這個對不對 根據debug設計的 然後出對是t 而不是node 不知道你是不是也表達這個意思
單純的enq感覺和並發並沒什麼關係,只是雙向鍊錶的建立。 java裡的鍊錶和C++中並沒什麼不同,只是java將pointer封裝成了reference,實際上起的依然是pointer的作用。 Node t可以抽像地看成新插入節點的前一個節點,在隊列中先入先出,自然新節點是在隊尾插入的,所以Node t = tail。先不考慮空隊列的情況,一個隊列有節點入隊,先處理好該新節點的pre, next,所以node.pre = tail; node.next = null;。然後將前一個節點的next指向新節點,也就是node,t.next = node。接下來考慮空隊列,這裡強行用一個new Node()初始化了隊列,此時tail == head。至於沒有將新插入節點繼續插入,我不了解這樣做的原因,直覺上,compareAndSetHead(node)比較正常一點。 當然,沒有像單執行緒佇列直接改變pre, next值,而是封裝到comapreAndSet*函數中,多執行緒的互斥應該是在這裡維護的。
哈,那個enq方法,你現在應該是看不懂的,沒專門學過的話,估計沒幾個人看得懂。要學無鎖同步,是多線程中的很高級的內容了。
@dj鄭豆漿 不知道這個對不對 根據debug設計的 然後出對是t 而不是node 不知道你是不是也表達這個意思
單純的enq感覺和並發並沒什麼關係,只是雙向鍊錶的建立。 java裡的鍊錶和C++中並沒什麼不同,只是java將pointer封裝成了reference,實際上起的依然是pointer的作用。
Node t可以抽像地看成新插入節點的前一個節點,在隊列中先入先出,自然新節點是在隊尾插入的,所以Node t = tail。先不考慮空隊列的情況,一個隊列有節點入隊,先處理好該新節點的pre, next,所以node.pre = tail; node.next = null;。然後將前一個節點的next指向新節點,也就是node,t.next = node。接下來考慮空隊列,這裡強行用一個new Node()初始化了隊列,此時tail == head。至於沒有將新插入節點繼續插入,我不了解這樣做的原因,直覺上,compareAndSetHead(node)比較正常一點。
當然,沒有像單執行緒佇列直接改變pre, next值,而是封裝到comapreAndSet*函數中,多執行緒的互斥應該是在這裡維護的。
哈,那個enq方法,你現在應該是看不懂的,沒專門學過的話,估計沒幾個人看得懂。要學無鎖同步,是多線程中的很高級的內容了。