1

在我的程序中,有 4 个线程同时将元素添加到 jlist 的模型中。由于更新或重绘太多,这会导致 jlist 闪烁、抛出异常甚至崩溃。

我试图拖延一些时间来解决我的问题,但我浪费了很多宝贵的时间。

我能做些什么?

这段代码模拟了我的问题:

new Thread(new Runnable() {
    @Override
    public void run() {
        for(int i=0; i<4; i++){
            new Thread(new Runnable() {
                @Override
                public void run() {
                    for(int o=0; o<2000; o++){
                        model.addElement("add");
                        try {
                            Thread.sleep(100);
                        } catch (InterruptedException ex) {
                            Logger.getLogger(NewJFrame.class.getName()).log(Level.SEVERE, null, ex);
                        }
                    }
                }
            }).start();
        }
   }
}).start();
4

3 回答 3

2

model.addElement("add"); 应该是这样的:

SwingUtilities.invokeLater(new Runnable() {
    public void run() {
        listModel.addElement("add");
    }
});

这样,您可以确保元素是在 EDT 下添加的,而不是在某个随机线程中。

于 2012-10-18T18:29:27.673 回答
1

GUI 操作只能在事件调度线程上执行。即使您创建了许多线程,也要对它们进行非 GUI 工作,然后触发 actionCommand(或类似的东西)来操作 GUI 方面。

您将在 Java 文档中多次阅读此警告: Swing 组件不是线程安全的

于 2012-10-18T18:17:17.577 回答
1

为了避免过多的刷新/重绘,您必须在后台线程中进行模型更新,并使用之前公开的技术将一次复制到 EDT 中的摇摆模型中。我建议不要使用 DefaultListModel,而是自定义处理 addAll()。

SwingUtilities.invokeLater(new Runnable() {
    public void run() {
        listModel.addAll( backgroundModel ); // only one fireDataChanged() fired
    }
});
于 2012-10-18T21:33:10.150 回答