JTable - 向排序表添加行会产生NullPointerException

时间:2015-04-17 21:18:24

标签: java nullpointerexception jtable tablesorter event-dispatch-thread

我在GUI中创建了一个JTable和8个不同的按钮。 根据您按下的按钮,表格将填充不同的数据(总是相同的列),在此之前它会删除所有旧数据(来自按下按钮)

一切正常 - 直到我正在排序一列。

我正在使用此代码为我的表设置分拣机:

    TableRowSorter<DefaultTableModel> sorter = new TableRowSorter<DefaultTableModel>(model);
    table.setRowSorter(sorter);

此代码用于计算/添加新行:

button.addActionListener(new ActionListener() {
        public void actionPerformed(ActionEvent arg0) {

            model.setRowCount(0);

            new Thread(new Runnable(){
                public void run(){

                    // Here is a call to another class which is calculating 
                    // the values and adding the row, but basically it is just.. 
                    // adding a row , so i exchanged it with this:

                    model.addRow(Object[]);

                }
            }).start();
        }
    });

正如我所说,当我对列进行排序时,会出现的异常,默认排序不会抛出任何异常。

我已经阅读过有关EDT的内容,我正在使用这种代码编辑它之外的表格,也许使用InvokeLater。 试图使用它,并阅读有关它的一些文档,但我无法使它工作。

从这里获得信息: Sorting JTable causes NullPointerException

对我来说,这是一个新的领域,告诉我&#34;只需添加xyz或做xyz&#34;不会帮助我,因为我不知道应该怎么做,这意味着如果有人可以给我一些例子甚至将它添加到我的代码中,那将是非常好的

这是我得到的例外(它重复几次):

  

线程中的异常&#34; AWT-EventQueue-0&#34;显示java.lang.NullPointerException     在javax.swing.DefaultRowSorter.convertRowIndexToModel(未知   来源)在javax.swing.JTable.convertRowIndexToModel(未知来源)     在javax.swing.JTable.getValueAt(未知来源)at   javax.swing.JTable.prepareRenderer(未知来源)at   javax.swing.plaf.basic.BasicTableUI.paintCell(未知来源)at   javax.swing.plaf.basic.BasicTableUI.paintCells(未知来源)at at   javax.swing.plaf.basic.BasicTableUI.paint(未知来源)at   javax.swing.plaf.ComponentUI.update(未知来源)at   javax.swing.JComponent.paintComponent(未知来源)at   javax.swing.JComponent.paint(未知来源)at   javax.swing.JComponent.paintChildren(未知来源)at   javax.swing.JComponent.paint(未知来源)at   javax.swing.JViewport.paint(未知来源)at   javax.swing.JComponent.paintChildren(未知来源)at   javax.swing.JComponent.paint(未知来源)at   javax.swing.JComponent.paintToOffscreen(未知来源)at   javax.swing.RepaintManager中的$ PaintManager.paintDoubleBuffered(未知   来自)javax.swing.RepaintManager $ PaintManager.paint(未知   来源)在javax.swing.RepaintManager.paint(未知来源)at   javax.swing.JComponent._paintImmediately(未知来源)at   javax.swing.JComponent.paintImmediately(未知来源)at   javax.swing.RepaintManager $ 4.run(未知来源)at   javax.swing.RepaintManager $ 4.run(未知来源)at   java.security.AccessController.doPrivileged(Native Method)at   java.security.ProtectionDomain $ 1.doIntersectionPrivilege(未知   来源)在javax.swing.RepaintManager.paintDirtyRegions(未知   来源)在javax.swing.RepaintManager.paintDirtyRegions(未知   来自)javax.swing.RepaintManager.prePaintDirtyRegions(未知   来源)在javax.swing.RepaintManager.access $ 1300(未知来源)at   javax.swing.RepaintManager $ ProcessingRunnable.run(未知来源)at   java.awt.event.InvocationEvent.dispatch(未知来源)at   java.awt.EventQueue.dispatchEventImpl(未知来源)at   java.awt.EventQueue.access $ 500(未知来源)at   java.awt.EventQueue $ 3.run(未知来源)at   java.awt.EventQueue $ 3.run(未知来源)at   java.security.AccessController.doPrivileged(Native Method)at   java.security.ProtectionDomain $ 1.doIntersectionPrivilege(未知   来自)java.awt.EventQueue.dispatchEvent(未知来源)at   java.awt.EventDispatchThread.pumpOneEventForFilters(未知来源)     at java.awt.EventDispatchThread.pumpEventsForFilter(Unknown Source)     在java.awt.EventDispatchThread.pumpEventsForHierarchy(未知   来自java.awt.EventDispatchThread.pumpEvents(未知来源)     at java.awt.EventDispatchThread.pumpEvents(Unknown Source)at   java.awt.EventDispatchThread.run(未知来源)

2 个答案:

答案 0 :(得分:1)

model.addRow(Object[]);看起来很可疑。您正在添加没有数据的行。

另外你应该在UI线程中这样做。使用SwingUtilities.invokeLater

而不是

new Thread(new Runnable(){
    public void run(){

DO

SwingUtilities.invokeLater(new Runnable(){
    public void run(){

答案 1 :(得分:1)

不要这样做......

        new Thread(new Runnable(){
            public void run(){

                // Here is a call to another class which is calculating 
                // the values and adding the row, but basically it is just.. 
                // adding a row , so i exchanged it with this:

                model.addRow(Object[]);

            }
        }).start();

这是在事件调度线程的上下文之外修改UI的状态,这导致UI,模型和分类器之间的竞争条件。

Swing不是线程安全的,UI的任何修改(或可能影响UI的任何内容)都应该在EDT的上下文中完成。

使用SwingUtilities.invokeLaterSwingWorker

有关详细信息,请参阅Concurrency in Swing