Thread View: pl.comp.lang.java
11 messages
11 total messages
Started by pamysz
Thu, 17 Nov 2011 16:01
Dodawanie do kolejki SynchronousQueue
Author: pamysz
Date: Thu, 17 Nov 2011 16:01
Date: Thu, 17 Nov 2011 16:01
70 lines
3604 bytes
3604 bytes
W momencie wykonywania instrukcji : kolejkaSQ.put(obiekt) program
zawiesza się.
Dla kolejki LinkedBlockingQueue wszystko jest ok.
Kiedyś (przed reinstalacją NB i JDK) wszystko działało.
Teraz jest NetBeans 7.0.1, Java 1.6.0_24.
Poniżej kod klasy:
package testkolejki;
import java.util.concurrent.LinkedBlockingQueue;
import java.util.concurrent.SynchronousQueue;
import java.util.logging.Level;
import java.util.logging.Logger;
public class TestKolejki {
class OnOf {
boolean on;
public OnOf(boolean on)
{
this.on = on;
}
}
public static void main(String[] args)
{
LinkedBlockingQueue<OnOf> kolejkaLQ = new
LinkedBlockingQueue();
SynchronousQueue<OnOf> kolejkaSQ = new SynchronousQueue();
TestKolejki tk = new TestKolejki();
OnOf o1 = tk.new OnOf(true);
OnOf o2 = tk.new OnOf(false);
OnOf oN = tk.new OnOf(false);
//----------------------------------------------------------------------
System.out.println("1. Kolejka LQ pusta = " +
kolejkaLQ.isEmpty());
System.out.println("1. Kolejka SQ pusta = " +
kolejkaSQ.isEmpty());
System.out.println("Adres ok1 = " + o1.hashCode() + ", " +
o1.toString());
System.out.println("Adres ok2 = " + o2.hashCode() + ", " +
o2.toString());
System.out.println("---------- Koniec deklaracji
-----------------------------------------");
try
{
kolejkaLQ.put(o2);
System.out.println("2. Kolejka LQ pusta = " +
kolejkaLQ.isEmpty());
kolejkaSQ.put(o1);// tutaj program się wiesza
System.out.println("2. Kolejka SQ pusta = " +
kolejkaSQ.isEmpty());
System.out.println("---------- Koniec dodawania do kolejki
-----------------------------------------");
oN = kolejkaLQ.take();
} catch (InterruptedException ex) {
System.out.println("Błąd !!!!!!!!!!!!!!!!!");
Logger.getLogger(TestKolejki.class.getName()).log(Level.SEVERE, null,
ex);
}
System.out.println("3. Kolejka LQ pusta = " +
kolejkaLQ.isEmpty() + ", okN: " + oN.toString());
System.out.println("3. Kolejka SQ pusta = " +
kolejkaSQ.isEmpty());
System.out.println("-------- Koniec programu
-------------------------------------------");
//----------------------------------------------------------------------
}
}
Z góry dziękuję za pomoc.
Re: Dodawanie do kolejki SynchronousQueue
Author: nullpointer
Date: Thu, 17 Nov 2011 16:33
Date: Thu, 17 Nov 2011 16:33
7 lines
1093 bytes
1093 bytes
Pierwsze zdanie w javadocu klasy SynchronousQueue (wytłuszczenie moje): A blocking queue in which *each put must wait for a take, and vice versa*. Jaki konkretnie jest Twój problem? ;-) -- npe
Re: Dodawanie do kolejki SynchronousQueue
Author: pamysz
Date: Thu, 17 Nov 2011 17:00
Date: Thu, 17 Nov 2011 17:00
18 lines
1935 bytes
1935 bytes
On Nov 17, 5:33 pm, nullpointer <i....@nie.dojdzie.pl> wrote:
> Pierwsze zdanie w javadocu klasy SynchronousQueue (wytłuszczenie moje):
>
> A blocking queue in which *each put must wait for a take, and vice versa*.
>
> Jaki konkretnie jest Twój problem? ;-)
> --
> npe
Jak uruchamiam ten programik w NB, to po:
System.out.println("2. Kolejka LQ pusta = " + kolejkaLQ.isEmpty());
program czeka jakby na zwolnienie kolejki (jednoelementowa jest), ale
wcześniej do niej nic nie dodawałem:
a zachowuje się jakby już nie była pusta.
Żadnego komunikatu, nic.
Jak wykomentuję linię:
kolejkaSQ.put(o1);// tutaj program się wiesza
to program wykonuje się dalej.
Re: Dodawanie do kolejki SynchronousQueue
Author: nullpointer
Date: Thu, 17 Nov 2011 17:19
Date: Thu, 17 Nov 2011 17:19
12 lines
1428 bytes
1428 bytes
No to jeszcze raz, jak krowie na rowie. Każy *put* wywołany na SynchronousQueue zablokuje się do momentu, aż ktoś (czytaj: inny wątek) wywoła *take* i odbierze element. To jest jasno opisane w javadoc, którego nie przeczytałeś, albo nie rozumiesz działania kolejek blokujących w ogóle i nie wpadłeś na to aby stworzyć dwa wątki (poczytaj o wzorcu Producer/Consumer). P.S. NetBeans nie ma nic do tego. -- npe
Re: Dodawanie do kolejki SynchronousQueue
Author: pamysz
Date: Thu, 17 Nov 2011 17:58
Date: Thu, 17 Nov 2011 17:58
46 lines
3467 bytes
3467 bytes
On Nov 17, 6:19 pm, nullpointer <i....@nie.dojdzie.pl> wrote:
> No to jeszcze raz, jak krowie na rowie.
>
> Ka y *put* wywo any na SynchronousQueue zablokuje si do momentu, a
> kto (czytaj: inny w tek) wywo a *take* i odbierze element. To jest
> jasno opisane w javadoc, kt rego nie przeczyta e , albo nie rozumiesz
> dzia ania kolejek blokuj cych w og le i nie wpad e na to aby stworzy
> dwa w tki (poczytaj o wzorcu Producer/Consumer).
>
> P.S. NetBeans nie ma nic do tego.
>
> --
> npe
Przeczytałem, ale chyba bez prawidłowego zrozumienia ;)
W programie (nie w tym) wątek dodaje obiekt do kolejki, a 2 wątek go
odczytuje.
Tutaj tylko dla testów stworzyłem klase jw. bo program zaczął się
wieszać w miejscu dodawania do kolejki SynchronousQueue.
Program skompilowany parę miesięcy temu działa prawidłowo.
Teraz dodawałem nowy wątek robiący to samo i program zaczął się
wieszać w momencie dodawania do kolejki w wątku który działał.
Moim zdaniem wątek powinien dodać do pustej kolejki i nie czekać na
odebranie z kolejki przez inny wątek tylko dalej się wykonywać.
Wyżej dla testów tworzę kolejkę, wyświetlam, że jest pusta i zapisuję
do kolejki 1 obiekt.
Chcę, żeby wypisał się komunikat, że zapisało do kolejki, ale program
czeka.
Według ciebie czeka, aż inny wątek zwolni kolejkę? Po co. Jego to nie
powinno interesować.
Wątek nie może wykonać put, gdy kolejka jest pełna, a take gdy jest
pusta - wtedy czeka.
Dlaczego ten sam wątek nie może zapisać do kolejki wyświetlić
komunikat i potem tego odczytać?
Byle najpierw zapisywał do pustej potem zwalniał i tak w kółko
Dla LinkedBlockingQueue robi to bez problemu, nie czeka na zwolnienie
tylko wyświetla komunikat.
kolejkaSQ.put(o1);// zapisanie do kolejki
System.out.println("zapisano"); // wyświetlenie komunikatu "zapisano".
Nie wyświetla "zapisano" dla SynchronousQueue.
kolejkaSQ.put(o1);// zapisanie do kolejki
o1 = kolejkaSQ.take();// pobranie z kolejki
System.out.println("zapisano");
też nie wyświetla "zapisano" tylko czeka w linii put.
Re: Dodawanie do kolejki SynchronousQueue
Author: pamysz
Date: Thu, 17 Nov 2011 18:04
Date: Thu, 17 Nov 2011 18:04
2 lines
1542 bytes
1542 bytes
Czyli krótko mówiąc ten sam wątek nie może wykonać metody put, a potem take na tej samej kolejce SynchronousQueue ?
Re: Dodawanie do kolejki SynchronousQueue
Author: nullpointer
Date: Thu, 17 Nov 2011 19:04
Date: Thu, 17 Nov 2011 19:04
26 lines
1785 bytes
1785 bytes
W dniu 2011-11-17 18:58, pamysz pisze: > Moim zdaniem wątek powinien dodać do pustej kolejki i nie czekać na > odebranie z kolejki przez inny wątek tylko dalej się wykonywać. Tak działa LinkedBlockingQueue. > Według ciebie czeka, aż inny wątek zwolni kolejkę? Po co. Jego to nie > powinno interesować. Tak działa SynchronousQueue. > Wątek nie może wykonać put, gdy kolejka jest pełna, a take gdy jest > pusta - wtedy czeka. Tak działa LinkedBlockingQueue. > Dlaczego ten sam wątek nie może zapisać do kolejki wyświetlić > komunikat i potem tego odczytać? Tak działa SynchronousQueue. Pytanie: Po co w ogóle używasz SynchronousQueue? -- npe
Re: Dodawanie do kolejki SynchronousQueue
Author: nullpointer
Date: Thu, 17 Nov 2011 19:12
Date: Thu, 17 Nov 2011 19:12
23 lines
2049 bytes
2049 bytes
W dniu 2011-11-17 19:04, pamysz pisze: > Czyli krótko mówiąc ten sam wątek nie może wykonać metody put, a potem > take na tej samej kolejce SynchronousQueue ? No nareszcie... * *) Oczywiście to jest tylko pół prawdy. Wątek może wykonać put, a następnie take na tej samej SQ, pod warunkiem, że po tym put, jakiś drugi wątek wywoła take, a następnie put na tej kolejce. Wtedy take wykonany w wątku pierwszym pobierze ci obiekt "zaputowany" w wątku drugim. Zrobić tego bez dodatkowego, drugiego wątku się nie da** bo wywołanie put w wątku pierwszym zablokuje go do momentu wywołania take w wątku drugim. **) Oczywiście zamiast wywołania take w wątku drugim, można na wątku pierwszym wywołać interrupt() i wtedy put zakończy się wyjątkiem InterruptedException, który możesz obsłużyć i "jechać dalej" w wątku pierwszym z czym tam sobie zaimplementujesz. Zamotałem Ci wystarczająco? ;) -- npe
Re: Dodawanie do kolejki SynchronousQueue
Author: pamysz
Date: Thu, 17 Nov 2011 19:40
Date: Thu, 17 Nov 2011 19:40
5 lines
1753 bytes
1753 bytes
Dzięki, czyli jeśli zależy mi, aby kolejka była 1 elementowa muszę zastosować bodajże ArrayBlockingQueue[1] ? by nie blokować wątku po put? Najgorsze, że program działał "poprawnie", ale nie według moich zamierzeń.
Re: Dodawanie do kolejki SynchronousQueue
Author: nullpointer
Date: Thu, 17 Nov 2011 20:56
Date: Thu, 17 Nov 2011 20:56
14 lines
1513 bytes
1513 bytes
W dniu 2011-11-17 20:40, pamysz pisze: > Dzięki, czyli jeśli zależy mi, aby kolejka była 1 elementowa muszę > zastosować bodajże ArrayBlockingQueue[1] ? by nie blokować wątku po > put? Tak > Najgorsze, że program działał "poprawnie", ale nie według moich > zamierzeń. Bo nie czytasz dokumentacji ;) -- npe
Re: Dodawanie do kolejki SynchronousQueue
Author: pamysz
Date: Thu, 17 Nov 2011 21:04
Date: Thu, 17 Nov 2011 21:04
20 lines
2046 bytes
2046 bytes
On Nov 17, 9:56 pm, nullpointer <i....@nie.dojdzie.pl> wrote: > W dniu 2011-11-17 20:40, pamysz pisze: > > > Dzięki, czyli jeśli zależy mi, aby kolejka była 1 elementowa muszę > > zastosować bodajże ArrayBlockingQueue[1] ? by nie blokować wątku po > > put? > > Tak > > > Najgorsze, że program działał "poprawnie", ale nie według moich > > zamierzeń. > > Bo nie czytasz dokumentacji ;) > > -- > npe Czytałem, ale najwyraźniej bez zrozumienia. Wtórny analfabetyzm, czy co :) W każdym razie jeszcze raz dzięki.
Thread Navigation
This is a paginated view of messages in the thread with full content displayed inline.
Messages are displayed in chronological order, with the original post highlighted in green.
Use pagination controls to navigate through all messages in large threads.
Back to All Threads