Очередь не работает с потоком?

У меня есть следующий код, который извлекает первый элемент из очереди, только если в нем есть как минимум 2 элемента. По какой-то причине он не опрашивает первый элемент. Однако, если я добавлю туда оператор печати, он будет печатать и опрашивать. Метод находится в потоке, и есть еще один поток, добавляющий элемент в очередь, этот поток читает из очереди.

...
public void run(){
    while(beginning){
        int size = queue.size();
        // adding this will cause the program to enter if below: System.out.println(size);
        if(size > 1){
            System.out.println("data: " + queue.poll());
            beginning = false;
        }
    }
}
...

Если добавить оператор println, он напечатает
1
1
....
2
data: data

Если Оператор println удален, он ничего не напечатает.

На самом деле, пока я добавляю туда что-нибудь, thread.sleep(1) или случайный оператор печати, он будет опрашивать данные и печатать их.

Спасибо за любой вклад.


person user433500    schedule 15.09.2010    source источник
comment
возможный дубликат Цикл не видит измененное значение без оператора печати   -  person Boann    schedule 25.08.2014


Ответы (4)


Вам нужно синхронизировать объект очереди:

public void run(){ 
    while(beginning){ 
        synchronized (queue) {
            int size = queue.size(); 
            // adding this will cause the program to enter if below: System.out.println(size); 
            if(size > 1){ 
                System.out.println("data: " + queue.poll()); 
                beginning = false; 
            } 
        } 
    }
} 

Это предотвратит доступ нескольких потоков к очереди в неподходящее время.

Вам также придется синхронизировать поток, добавляющий элементы в очередь, аналогичным образом.

person Starkey    schedule 15.09.2010

Похоже на проблему с синхронизацией.

person Dheeraj Joshi    schedule 15.09.2010

Вы должны быть осторожны при использовании общего ресурса между потоками. Вам следует подумать об использовании блокировки (токена), получить ее перед доступом к очереди и освободить после использования.

person Jorge Niedbalski R.    schedule 15.09.2010

... оказалось, что я должен синхронизировать поток, чтобы он работал, потому что очередь реализована связанным списком.

Но почему оператор печати заставит его работать?

person user433500    schedule 15.09.2010