ArrayIndexOutOfBoundsException:在JTable创建/ tablechanged上为-1 [英] ArrayIndexOutOfBoundsException: -1 on JTable creation/tablechanged
问题描述
我已经阅读了所有线程,看起来好像可以解决我的问题,我也在这里阅读了所有的答案,但我仍然在我的智慧结束。我不确定为什么抛出异常,虽然我觉得这可能与 threading
有关。如果有,请告诉我在哪里包含 new Runnable()
以及是否 invokeLater()
或 invokeAndWait()
,因为我试过它无济于事。
I have read through all the threads out there that looked as if they could solve my problem and I've also read all the answers on here, but I'm still at my wit's end. I'm not sure why the exception is thrown, although I have a feeling this might be to do with threading
. If it does, please let me know where to include the new Runnable()
and whether to invokeLater()
or invokeAndWait()
, as I have tried it to no avail.
在我给你代码时请耐心等待我导致异常+堆栈跟踪(下面)。
Please bear with me while I give you the code that leads to the exception + the stacktrace (below).
编辑:我已经包含了一些 syso <在$ code> tableChanged
被调用之前, AnnoTable
部分中的/ code> s并且它们未显示在控制台,因此我认为问题必须在应用程序到达那一点之前发生,即从 AAView
调用它或者实例化数据和表模型时...
EDIT: I had included a number of syso
s in the AnnoTable
section just before tableChanged
is called and they don't show up in the console, hence I think the problem must occur even before the application gets to that point, i.e. either when it's called from AAView
or when data and table model are instantiated...
编辑II :问题是被覆盖的 tableChanged
方法。那显然会引发异常。我已经删除了 tableChanged()
调用(这也没有什么区别)。现在我还有另一个问题:了解底层数据的变化( AnnoData
)如何自动更新表格。虽然这可能是针对另一个查询(在扩展的Google搜索之后),但请随时在此主题中发布有用的评论,因为我将继续阅读它...感谢所有有用的评论和提示!
EDIT II: The problem was the overwritten tableChanged
method. That would obviously fire an Exception. I've removed the tableChanged()
call (which wouldn't make a difference) as well. Now I've got another problem: understanding how a change in the underlying data (AnnoData
) can automatically update the table. Although this is perhaps for another query (after an extended Google search), please feel free to post helpful comments in this thread, as I'll continue reading it... THANKS A LOT for all the helpful comments and tips!
编辑III:* 我已经解决了这个问题。我需要从 AnnoData
中实例化另一个对象,将其传递给 AnnoTableModel
的新实例,将此实例设置为我的表然后 fireTableDataChanged()
。
EDIT III:* I've solved the problem. I needed to instantiate another object from AnnoData
, pass that to a new instance of AnnoTableModel
, set this instance to my table and THEN fireTableDataChanged()
.
编辑IV:好的,所以 fireTableDataChanged()
(在编辑III中使用)毕竟是不必要的。我仍然想要使用它而不是一直创建新对象。我想我应该问一个新问题...谢谢!
EDIT IV: Okay, so fireTableDataChanged()
(as used in EDIT III) is unnecessary after all. I still would want to use it rather than creating new objects all the time. I guess I should ask a new question... Thanks!
AAView
中的这个方法应该创建一个对象扩展一个 JTable
,把它放到 JScrollPane
等等(后者确实有效)。
This method in AAView
should create an object extending a JTable
, put it into a JScrollPane
, etc. (the latter does work).
private JPanel createAnnoTablePanel() {
annoTablePanel = new JPanel();
annoTable = new AnnoTable(aameth);
setAnnoTable(annoTable);
JScrollPane scrollPane = new JScrollPane(getAnnoTable());
annoTablePanel.add(scrollPane);
return annoTablePanel;
}
这是类 AnnoTable
( aameth
是一个包含访问数据模型的业务逻辑的实例对象,工作正常)。
Here is the class AnnoTable
(aameth
is an instance object containing business logic to access a data model, works fine).
public class AnnoTable extends JTable implements TableModelListener
{
public AnnoTable(AAMethods aameth)
{
int tokenCount = aameth.getTokenCount();
AnnoData annoData = new AnnoData(aameth); // cf. below, AnnoData is a Vector(Vector<Object>,String[])
TableModel tableModel = new AnnoTableModel(annoData.getAnnoData(),
// AnnoTableModel extends AbstractTableModel(Vector, String[])
annoData.getColTitles());
setModel(tableModel);
getModel().addTableModelListener(this);
TableModelEvent tme = new TableModelEvent(tableModel);
this.tableChanged(tme);
setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
setCellSelectionEnabled(true);
getColumnModel().getSelectionModel().addListSelectionListener(new AnnoTableSelectionListener(this));
setPreferredScrollableViewportSize(this.getPreferredSize());
}
public void tableChanged(TableModelEvent e) {
int row = e.getFirstRow();
int column = e.getColumn();
AbstractTableModel model = (AbstractTableModel)e.getSource();
String columnName = model.getColumnName(column);
Object data = model.getValueAt(row, column); // This is where the exception is thrown!
}
}
如果您需要<$ c $的源代码c> AnnoTableModel()(这是 AbstractTableModel
的相当通用的扩展名)或 AnnoData
(构造一个 Vector
,其中包含三个 Vector< Object>
和一个 String []
列标题),请告诉我。
If you need the source code for AnnoTableModel()
(which is a fairly generic extension of AbstractTableModel
) or AnnoData
(which constructs a Vector
containing three Vector<Object>
and a String[]
for column titles), please let me know.
这是堆栈跟踪。
Exception in thread "AWT-EventQueue-0" java.lang.ArrayIndexOutOfBoundsException: -1
at java.util.Vector.elementAt(Unknown Source)
at javax.swing.table.DefaultTableModel.getValueAt(Unknown Source)
at package.AnnoTable.tableChanged(AnnoTable.java:52)
at javax.swing.JTable.setModel(Unknown Source)
at javax.swing.JTable.<init>(Unknown Source)
at javax.swing.JTable.<init>(Unknown Source)
at package.AnnoTable.<init>(AnnoTable.java:25)
at package.AAView.createAnnoTablePanel(AAView.java:464)
at package.AAView.createNorthPanel(AAView.java:455)
at package.AAView.displayAndAnnotate(AAView.java:444)
at package.AAView.loadProject(AAView.java:333)
at package.AAView.actionPerformed(AAView.java:286)
at javax.swing.AbstractButton.fireActionPerformed(Unknown Source)
at javax.swing.AbstractButton$Handler.actionPerformed(Unknown Source)
at javax.swing.DefaultButtonModel.fireActionPerformed(Unknown Source)
at javax.swing.DefaultButtonModel.setPressed(Unknown Source)
at javax.swing.AbstractButton.doClick(Unknown Source)
at javax.swing.AbstractButton.doClick(Unknown Source)
at javax.swing.plaf.basic.BasicMenuItemUI$Actions.actionPerformed(Unknown Source)
at javax.swing.SwingUtilities.notifyAction(Unknown Source)
at javax.swing.JComponent.processKeyBinding(Unknown Source)
at javax.swing.JMenuBar.processBindingForKeyStrokeRecursive(Unknown Source)
at javax.swing.JMenuBar.processBindingForKeyStrokeRecursive(Unknown Source)
at javax.swing.JMenuBar.processBindingForKeyStrokeRecursive(Unknown Source)
at javax.swing.JMenuBar.processKeyBinding(Unknown Source)
at javax.swing.KeyboardManager.fireBinding(Unknown Source)
at javax.swing.KeyboardManager.fireKeyboardAction(Unknown Source)
at javax.swing.JComponent.processKeyBindingsForAllComponents(Unknown Source)
at javax.swing.JComponent.processKeyBindings(Unknown Source)
at javax.swing.JComponent.processKeyEvent(Unknown Source)
at java.awt.Component.processEvent(Unknown Source)
at java.awt.Container.processEvent(Unknown Source)
at java.awt.Component.dispatchEventImpl(Unknown Source)
at java.awt.Container.dispatchEventImpl(Unknown Source)
at java.awt.Component.dispatchEvent(Unknown Source)
at java.awt.KeyboardFocusManager.redispatchEvent(Unknown Source)
at java.awt.DefaultKeyboardFocusManager.dispatchKeyEvent(Unknown Source)
at java.awt.DefaultKeyboardFocusManager.preDispatchKeyEvent(Unknown Source)
at java.awt.DefaultKeyboardFocusManager.typeAheadAssertions(Unknown Source)
at java.awt.DefaultKeyboardFocusManager.dispatchEvent(Unknown Source)
at java.awt.Component.dispatchEventImpl(Unknown Source)
at java.awt.Container.dispatchEventImpl(Unknown Source)
at java.awt.Window.dispatchEventImpl(Unknown Source)
at java.awt.Component.dispatchEvent(Unknown Source)
at java.awt.EventQueue.dispatchEventImpl(Unknown Source)
at java.awt.EventQueue.access$000(Unknown Source)
at java.awt.EventQueue$1.run(Unknown Source)
at java.awt.EventQueue$1.run(Unknown Source)
at java.security.AccessController.doPrivileged(Native Method)
at java.security.AccessControlContext$1.doIntersectionPrivilege(Unknown Source)
at java.security.AccessControlContext$1.doIntersectionPrivilege(Unknown Source)
at java.awt.EventQueue$2.run(Unknown Source)
at java.awt.EventQueue$2.run(Unknown Source)
at java.security.AccessController.doPrivileged(Native Method)
at java.security.AccessControlContext$1.doIntersectionPrivilege(Unknown Source)
at java.awt.EventQueue.dispatchEvent(Unknown Source)
at java.awt.EventDispatchThread.pumpOneEventForFilters(Unknown Source)
at java.awt.EventDispatchThread.pumpEventsForFilter(Unknown Source)
at java.awt.EventDispatchThread.pumpEventsForHierarchy(Unknown Source)
at java.awt.EventDispatchThread.pumpEvents(Unknown Source)
at java.awt.EventDispatchThread.pumpEvents(Unknown Source)
at java.awt.EventDispatchThread.run(Unknown Source)
我可以在那里看到 EDT
所以从我所知道的这可能真的是线程问题。但是,我不知道如何找到我应该在哪里开始新的 Thread
(或调用 new Runnable()
。
I can see the EDT
in there so from what I've learned this might really be a problem of threading. However, I don't know how to find out where I should start a new Thread
(or invoke a new Runnable()
.
在旁注中,当我更改 AnnoTable
以扩展<$ c时,Exception才开始出现$ c> JTable 而不是 JPanel
。原来我有 AnnoTable
不仅构建表但也将它包装在一个滚动窗格中并将其添加到新的 JPanel
。但是因为我想从一个 fireTableDataChanged
只知道 AAView
的类(其中还包含 setAnnoTable()
方法)我想以正确的方式做到这一点,在它工作之前就好了。墨菲定律?
On a side note, the Exception only started appearing when I changed AnnoTable
to extend JTable
rather than JPanel
. Originally I had AnnoTable
not only construct the table but also wrap it in a scroll pane and add this to a new JPanel
. But because I wanted to fireTableDataChanged
from a Class that only knew of AAView
(which also features a setAnnoTable()
method) I wanted to do it the correct way, whereas before it worked just fine. Murphy's law?
推荐答案
一个-1的rowIndex(== TableModelEvent.HEADER_ROW)表示模型的结构已完全改变。这样的事件由JTable在setModel上内部触发。阅读TableModelEvent的api文档以完全理解哪些类型/值期望在监听器的tableChanged。
A rowIndex of -1 (==TableModelEvent.HEADER_ROW) indicates that the model's structure has changed completely. Such an event is fired internally by the JTable on setModel. Read the api doc of TableModelEvent to fully understand which types/values to expect in the listener's tableChanged.
BTW,@ AKJ是对的 - 不需要在表代码中触发任何TableModelEvents。使模型适当地触发事件
BTW, @AKJ is right - no need to fire any TableModelEvents in your table code. Make the model fire the events as appropriate
这篇关于ArrayIndexOutOfBoundsException:在JTable创建/ tablechanged上为-1的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!