EventQueue inconsistent ID's
Asked Answered
S

1

4

I have a problem with the following example code that shows inconsistent behavior for the EventQueue:

public static void main( String[] args ) throws InvocationTargetException, InterruptedException {

    final long[] id1 = new long[ 1 ];
    final long[] id2 = new long[ 1 ];

    EventQueue.invokeAndWait( new Runnable() {
      @Override public void run() {
        id1[ 0 ] = Thread.currentThread().getId();
      }
    } );

    Thread.sleep( 5000 );

    EventQueue.invokeAndWait( new Runnable() {
      @Override public void run() {
        id2[ 0 ] = Thread.currentThread().getId();
      }
    } );

    System.out.println( "id1 = " + id1[0] );
    System.out.println( "id2 = " + id2[0] );

    if(id1[0]!=id2[0]){
      System.out.println("These ID's don't match, even though they were retrieved from the same thread.");
    }

  }

Basically, it gets the ID of the eventqueue thread, waits 5 seconds and then gets the ID again.

For some reason, the ID's won't match. Apparently, the EventQueue was destroyed and recreated. Is this normal behavior? Is this documented somewhere? Is it a bug? Even if it was a different instance, shouldn't it have the same ID?

If I don't perform the Thread.sleep, the ID's will match.

My other question is: How can I get around this? I'm using an object that can only be accessed on the creating thread. If this happens to be the eventqueue (which it doesn't necessarily have to be) I have to be able to check if it is still the eventqueue.

Sealed answered 25/8, 2011 at 12:25 Comment(0)
F
2

That AWT Event Dispatch Thread may be shut down when it's no longer needed (this page describes both the spectification and the behaviour of the actual implementation in JDK 7).

This seems to happen here: You use the system EventQueue to handle one event. Then nothing needs it any more (no AWT/Swing components, ...). After some time it is shut down.

Then, when you use the EventQueue again another thread is started to take over that role.

So what happens here is that your Runnable.run() methods do get executed on two distinct threads. Both threads are "the AWT Event Dispatch Thread", just at different times in the JVMs life-cycle.

Maybe special casing this by using EventQueue.isDispatchThread() would be a possible solution.

Flamboyant answered 25/8, 2011 at 12:35 Comment(2)
Thanks. I was hoping there would be a better way than a special check for the EventQueue thread itself, but I guess if I have to I have to. :)Sealed
Well, I'd say it is a special case in your requirement, since you want to treat two different event threads as if they were the same. If you really wanted to allow only the same thread access something, then leaving that check out and testing for thread id only would be sufficient.Flamboyant

© 2022 - 2024 — McMap. All rights reserved.