Java 我的代码的哪一部分在事件调度队列中

Java 我的代码的哪一部分在事件调度队列中,java,swing,event-handling,Java,Swing,Event Handling,在遇到这个问题之前,我一直以为我理解EDQ。我的代码如下所示。它从一个红色的读卡器读取数据。如果收到的第一个字符是“Z”,我将执行一组代码(显示一个JOptionPane),如果是0,我将执行另一段代码(显示另一个JOptionPane)。我试图在EDQ中实现这一点,因此我使用SwingUtilities调用EANDWAIT。当我测试这些错误条件时,条件中的第一条语句按设计工作,但在测试else子句时,我得到一个java错误。具体而言: 线程“AWT-EventQueue-2”java.lang

在遇到这个问题之前,我一直以为我理解EDQ。我的代码如下所示。它从一个红色的读卡器读取数据。如果收到的第一个字符是“Z”,我将执行一组代码(显示一个JOptionPane),如果是0,我将执行另一段代码(显示另一个JOptionPane)。我试图在EDQ中实现这一点,因此我使用SwingUtilities调用EANDWAIT。当我测试这些错误条件时,条件中的第一条语句按设计工作,但在测试else子句时,我得到一个java错误。具体而言:

线程“AWT-EventQueue-2”java.lang中出现异常。错误:无法从事件调度程序线程调用invokeAndWait 位于java.awt.EventQueue.invokeAndWait(未知源)

它都是同一条件的一部分。一个条款怎么可能是EDQ的一部分,而另一个条款怎么可能不是

这太疯狂了

谢谢你的帮助

艾略特

     while ((line = in.readLine()) != null) {
        if (line.charAt(0) == 'Z') {
            String theMsg;
            theMsg = "No records were found.";
            try {
                SwingUtilities.invokeAndWait(new DoShowDialog(null, theMsg, 0));
            } catch (java.lang.reflect.InvocationTargetException e1) {
                e1.printStackTrace();
            } catch (InterruptedException e2) {
                // TODO Auto-generated catch block
                e2.printStackTrace();
            }
            noDocs = true;
            Object args[] = new Object[1];
            args[0] = "1";
            window.call("uploadConfig", args);
            downloadAccount.setEnabled(true);
            uploadAccount.setEnabled(false);
            deleteAllUnselectedCodes.setEnabled(false);
            queue = null;
            if (poll) {
                polltimer.restart();
            }
        } else if (line.charAt(0) == 'O') {
            String theMsg;
            theMsg = "Account is currently checked out 
            by user "+ line.substring(1)
            + ".  You can view this 
            account but you cannot modify it. ";
            try {
                SwingUtilities.invokeAndWait(new DoShowDialog(null, theMsg, 0));
            } catch (java.lang.reflect.InvocationTargetException e1) {
                e1.printStackTrace();
            } catch (InterruptedException e2) {
                // TODO Auto-generated catch block
                e2.printStackTrace();
            }
            initialckBoxState = false;
            accountfoundandnotcheckedout = true;
            viewMode = true;
            patientpane.setEditFields(false);
            otherpane.setEditFields(false);
            getAccountImages(acctEntered); // bluenoble
        }
        .....................
        more stuff
    }

如果最终从事件处理程序调用,则从EDT调用(除非您使用swingworkers或显式创建线程/使用线程池,否则所有代码都将被调用)

检查堆栈跟踪以查找其来源


要修复它,请使用前面提到的并重写doInBackground(),您可以检查自己是否在调度线程中,执行不会跳转线程

因此,所有发布的代码都在EDT(事件调度线程)中运行,它拒绝调用EANDWAIT,因为这会导致固有的死锁。(实际上,它可以像.NET中的SynchronizationContexts一样转换为立即调用,但它并不是这样设计的。)

在这种特殊情况下,我怀疑代码是从EDT回调中调用的(并从另一个场景复制粘贴)。“琐碎的修复”(这将消除此异常)将消除
invokeAndWait
方法,但如果此代码也在EDT之外调用,则会产生负面影响——这两种情况的处理方式大不相同。请花一些时间确定此代码何时/何处运行以及运行原因

正如其他人所指出的,这段代码似乎有些混乱:如果它不在EDT上,那么操纵Swing对象是不好的,如果它在EDT上,那么就没有必要调用EANDWAIT,阻塞也是不好的

愉快的编码。

1)MSG看起来像疯了一样
theMsg=“someString”+localVariable+“anotherString”

2a)为什么在基本文件I/O中调用Swing GUI

2b)为什么在基本文件I/O中构建GUI

读取文件,关闭();finally块中的I/O流

3) 您创建了许多DoShowDialog(null,theMsg,0));,每个循环创建一个循环,以此类推

4) 在此I/O流之外的每一个正确和错误的移动

5) 如果是I/O流,则将每个事件加载到数组的某些部分

6) 您的代码可能会冻结GUI(如果存在)


7) 将所有流移动到后台任务

通常称为“EDT”而不是“EDQ”;)无论如何,我不知道是否有任何保证可以保证在代码的其余部分中从哪个线程进行调用,但您可以轻松解决您的问题:任何时候您需要调用一个必须(或不得)从EDT调用的方法,您都可以调用SwingUtilities.isEventDispatchThread()要验证您是否在EDT上…哪一行引发异常?您是否试图在EDT之外操作Swing组件(使用setEditFields和类似的方法调用)?您是否可以隔离错误并创建和发布一个?您是否建议从EDT调用相同的调用部分?这似乎表明这是一种命中或未命中的事情。@Elliott是的,任何函数都可以从任何活动线程调用检查节所在方法的调用层次结构(eclipse中有一个用于该方法的工具),以查看可以从中调用它的可能位置(和线程)