2010-10-14 64 views
2

我正試圖通過使用多線程的Java解決Java編寫器偏好的讀寫器問題。以下是我的代碼的簡化版本。它會起作用嗎?Java PriorityQueue等待

public PriorityQueue<myClass> pq; 
public void foo(){ 
    myClass obj = new myClass(); 
    pq.add(obj); 
    obj.wait(); 
    //Actual code 
} 
public void bar(){ 
    pq.remove().notify(); 
} 

假設優先級隊列pq最初是空的,並且封裝類的構造函數調用pq的構造函數。另外,先調用foo,然後調用bar。所以當foo被調用時,它將obj添加到隊列中,併成爲前端元素,以便在刪除的元素bar中調用remove時。我的問題是,是否會執行「實際代碼」?還是我在兩個完全不同的對象上執行wait()和notify()?如果是這樣,我該如何解決?

+0

你可以多說一下你想要發生什麼嗎? 「作家偏好」是什麼意思,特別是在示例代碼的上下文中?據推測'foo()'和'bar()'是從不同的線程中調用的......並且你希望'foo()'排入一個對象,然後阻塞直到bar()出列它。爲什麼? – andersoj 2010-10-15 04:44:08

+0

此外,這是如何涉及*非常*類似的問題在這裏http://stackoverflow.com/questions/3938606/waiting-on-objects-after-putting-them-into-priority-queue-in-java? – andersoj 2010-10-15 05:18:56

+0

這是同樣的問題。我已經等了大約10-12個小時,似乎沒有人迴應,所以我認爲這個問題已經排在了名單之後,讓任何人再次注意到,這就是爲什麼我再次發佈這個問題的原因。 – Anand 2010-10-17 09:28:15

回答

0

你應該注意到PriorityQueue不是線程安全的......即,如果同時調用foo和/或bar,它們可能會不可避免地破壞pq的內部狀態。

+0

假設我使用PriorityBlockingQueue。我的問題仍未解決。 – Anand 2010-10-14 05:08:10

0

我仍然試圖解析你的問題,到目前爲止我可以提取的是,你想實現一個優先隊列myClass,展示作家偏好。 Java的現成鎖定不提供嚴格的作者偏好,但如果您確定(可能是最好的),並使用近似的作者偏好,則可以在正常模式下使用正常的ReentrantReadWriteLock

寫完所有這些(並考慮了它可能出錯的多種方式)我真的很想知道爲什麼java.util.concurrentPriorityBlockingQueue實現不符合您的需要。

以下代碼遠未經過測試,但通過了我的1:00 AM嗅探測試。

private final PriorityQueue<myClass> pq = ...; 
// associated RW lock, in fair mode (==true) 
private final ReadWriteLock pqLock = new ReentrantReadWriteLock(true);  
private final Condition pqWriteCondition = pqLock.writeLock().newCondition();  

public void produceNew() 
{ 
    myClass obj = new myClass(); 
    pqLock.writeLock.lock(); 
    try { 
     pq.offer(obj); 
     pqWriteCondition.notifyAll(); 
    } finally { 
     pqLock.writeLock.unlock(); 
    } 
    //Actual code 
} 

public void consumeFirst() { 
    myClass consume = null; 
    pqLock.readLock.lock(); 
    try { 
     consume = pq.poll(); 
     while (consume == null) { 
     pqWriteCondition.wait(); 
     consume = pq.poll(); 
     } 
    } finally { 
     pqLock.readLock.unlock(); 
    } 
    //Actual code 

} 
+0

我的代碼無法正常工作,因爲我在執行等待和通知時沒有在適當的對象上使用同步塊。我相信你的代碼會遭遇類似的事情。 – Anand 2010-10-17 09:34:00

+0

有趣...不是我仔細測試過這個,但它與我在生產中使用的代碼類似。通常,對於受讀/寫鎖保護的對象,寫鎖定條件是正確的。你看過RWLock API嗎? – andersoj 2010-10-17 11:52:22

+0

此外,如果您不使用juconcurrent鎖定和條件,而是使用wait()和notify()來拋棄java監視器,這裏有一個相關的問題:http://stackoverflow.com/questions/ 3903039/wait-and-notify-method-always-illegalmonitorstateexception-is-happen-and-te/3951544#3951544 – andersoj 2010-10-17 11:54:45