標籤:while 解決辦法 特性 一個 生產者 指標 alt post name
一.
一個鎖掛多組監視器的情況,講述了java.util.concurrent.locks包裡面的lock介面和conditon介面的一些特點。
必須要明確,lock介面和condition介面有什麼作用。
有人說連個對象都沒有,老是說介面,自己實現嗎?lock和condition暴露的就是介面,我們就是在使用這個介面,並不實現。會實現嗎?不可能嘛。給我們介面,我們就能用,怎麼用?它怎麼實現,怎麼用。它自己在做實現,我直接拿它用就完事兒了。介面有擴充性。
API中不光介紹了概念,還給出了範例,協助我們學會使用相應的概念。
下面研究一下condition的範例(範例中用的都是變數,而不是生產者和消費者的概念),
BounderBuffer是緩衝區,裡面有一個鎖,兩個監視器,非滿,非空。之前定義的是name變數,記錄的是烤鴨的名字。這裡定義的是一個數組容器,這裡面放的是對象,object[],說白了人家是真正定義了能裝一百隻鴨子的筐。putptr是存,takeptr是取,count是計數,這些全都用來運算元組的變數。
這個buffer裡面一共有兩個方法,一個是存,一個是取。
這個存呢?就是你給我一隻鴨子(object x),進來後就拿到鎖了lock.lock();如果你拿到鎖了,在裡面的操作過程中,這哥們能取嗎?拿不到,這鎖是互斥的。你拿到,我就拿不到。現在,我們拿到鎖了,就進來開始判斷了,是while判斷。判斷標記的時候,一定要用while。為什麼要用while,因為安全。每一次醒來,都先判斷標記,這是最安全的做法,因為標記是否改動,誰都不知道。因此,每次醒過來,我都看一看,到底有沒有,有我就不做,沒有我就做。signal是不是All就不一定了,如果能實現喚醒對方,我根本不需要All,因為All會把本方喚醒。如果掛了多組監視器,就可以喚醒對方。把對方全喚醒,和喚醒一個還是有點區別的。把對方全喚醒,全都活了,但是只有一個在運行,運行完之後改標記,這時另外一個線程過來,判斷標記還是掛了,這個線程根本就不需要過來。那怎麼辦呢?喚醒一個就完事兒了,這是效率問題。count==items.length,計數器判斷的是數組的長度,如果相等,那麼就烤到位了,不用烤了直接await。沒烤滿呢?來一隻,存一隻,items[putptr]=x。putptr是指標。
JAVA-初步認識-第十四章-線程間通訊-多生產者多消費者問題-JDK1.5新特性解決辦法-範例