Java 删除行时出现 Swing AbstractTableModel-IndexOutOfBounds 异常
Java Swing AbstractTableModel-IndexOutOfBounds exception when deleting a row
我正在做一个 Swing 项目。可能,它太大而无法粘贴到这里。我什至尝试记录 table.getSelectedRow() 并且它显示了正确的索引。但不知何故,当我按下一个删除按钮时,这导致了在此 class 中调用的删除方法,selectedRow 更改为 -1,我得到了一个 IndexOutOfBoundsException。
请帮忙。这是 CarTableModelClass:
import javax.swing.table.AbstractTableModel;
import java.util.LinkedList;
public class CarTableModel extends AbstractTableModel {
public LinkedList<Car> cars=new LinkedList<Car>();
@Override
public int getRowCount() {
return cars.size();
}
@Override
public int getColumnCount() {
return 4;
}
@Override
public Object getValueAt(int row, int column){
if((row>cars.size()-1) || (column>3) ){
return null;
}
else {
Car targetCar=cars.get(row);
switch (column){
case 0: {return targetCar.brand;}
case 1: {return targetCar.year;}
case 2: { return targetCar.volume;}
case 3: {return targetCar.maxSpeed;}
default: {return null; }
}
}
}
@Override
public Class<?> getColumnClass(int columnIndex){
switch (columnIndex){
case 0: {return String.class;}
case 1: {return Integer.class;}
case 2: { return Double.class;}
case 3: {return Double.class;}
default: {return Object.class; }
}
}
@Override
public String getColumnName(int columnIndex){
switch (columnIndex){
case 0: {return "Brand";}
case 1: {return "Year";}
case 2: { return "Volume";}
case 3: {return "Max Speed";}
default: {return null; }
}
}
@Override
public boolean isCellEditable(int rowIndex, int columnIndex){
return false;
}
public void addRow(Car value)
{
if(value!=null) {
cars.add(value);
fireTableDataChanged();
}
}
public void update(int index, Car car){
if((car!=null) &&(index>=0)&& (index<(cars.size()-1))){
cars.set(index,car);
fireTableRowsUpdated(index,index+1);
}
}
public void remove(int index){
if((cars!=null) &&(index>=0)&& (index<(cars.size()-1))){
cars.remove(index);
fireTableRowsDeleted(index,index+1);
}
}
}
这里是我得到的例外情况:
Exception in thread "AWT-EventQueue-0" java.lang.IndexOutOfBoundsException: Index: -1, Size: 10
at java.util.LinkedList.checkElementIndex(LinkedList.java:555)
at java.util.LinkedList.get(LinkedList.java:476)
at CarTableModel.getValueAt(CarTableModel.java:26)
at MainWindow.lambda$new[=12=](MainWindow.java:51)
at javax.swing.DefaultListSelectionModel.fireValueChanged(DefaultListSelectionModel.java:184)
at javax.swing.DefaultListSelectionModel.fireValueChanged(DefaultListSelectionModel.java:164)
at javax.swing.DefaultListSelectionModel.fireValueChanged(DefaultListSelectionModel.java:211)
at javax.swing.DefaultListSelectionModel.removeIndexInterval(DefaultListSelectionModel.java:677)
at javax.swing.JTable.tableRowsDeleted(JTable.java:4509)
at javax.swing.JTable.tableChanged(JTable.java:4412)
at javax.swing.table.AbstractTableModel.fireTableChanged(AbstractTableModel.java:296)
at javax.swing.table.AbstractTableModel.fireTableRowsDeleted(AbstractTableModel.java:261)
at CarTableModel.remove(CarTableModel.java:83)
at Toolbar.actionPerformed(Toolbar.java:45)
at javax.swing.AbstractButton.fireActionPerformed(AbstractButton.java:2022)
at javax.swing.AbstractButton$Handler.actionPerformed(AbstractButton.java:2348)
at javax.swing.DefaultButtonModel.fireActionPerformed(DefaultButtonModel.java:402)
at javax.swing.DefaultButtonModel.setPressed(DefaultButtonModel.java:259)
at javax.swing.plaf.basic.BasicButtonListener.mouseReleased(BasicButtonListener.java:252)
at java.awt.Component.processMouseEvent(Component.java:6535)
at javax.swing.JComponent.processMouseEvent(JComponent.java:3324)
at java.awt.Component.processEvent(Component.java:6300)
at java.awt.Container.processEvent(Container.java:2236)
at java.awt.Component.dispatchEventImpl(Component.java:4891)
at java.awt.Container.dispatchEventImpl(Container.java:2294)
at java.awt.Component.dispatchEvent(Component.java:4713)
at java.awt.LightweightDispatcher.retargetMouseEvent(Container.java:4888)
at java.awt.LightweightDispatcher.processMouseEvent(Container.java:4525)
at java.awt.LightweightDispatcher.dispatchEvent(Container.java:4466)
at java.awt.Container.dispatchEventImpl(Container.java:2280)
at java.awt.Window.dispatchEventImpl(Window.java:2750)
at java.awt.Component.dispatchEvent(Component.java:4713)
at java.awt.EventQueue.dispatchEventImpl(EventQueue.java:758)
at java.awt.EventQueue.access0(EventQueue.java:97)
at java.awt.EventQueue.run(EventQueue.java:709)
at java.awt.EventQueue.run(EventQueue.java:703)
at java.security.AccessController.doPrivileged(Native Method)
at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:76)
at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:86)
at java.awt.EventQueue.run(EventQueue.java:731)
at java.awt.EventQueue.run(EventQueue.java:729)
at java.security.AccessController.doPrivileged(Native Method)
at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:76)
at java.awt.EventQueue.dispatchEvent(EventQueue.java:728)
at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:201)
at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:116)
at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:105)
at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:101)
at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:93)
at java.awt.EventDispatchThread.run(EventDispatchThread.java:82)
-1
UPD:这是第 51 行的 lambda:
table.getSelectionModel().addListSelectionListener((event)->
{
int row=table.getSelectedRow();
formPanel.setSelectedRow(row);
toolbar.setSelectedRow(row);
System.out.println(row);
formPanel.fill(
model.getValueAt(row,0),
model.getValueAt(row,1),
model.getValueAt(row,2),
model.getValueAt(row,3)
);
});
问题是,我无法阻止它返回 -1。
看起来该行已被 CarTableModel.remove
成功删除,但这会调用 fireTableRowsDeleted
,后者又会调用 MainWindow
中的某个方法,然后调用 CarTableModel.getValueAt
,但由于该行已被删除,它会引发异常。您已经测试过太大的行或列的值,然后从该方法中测试 return 而不做任何事情。如果您还测试负值,是否一切正常?
或者,正如@JBNeizet 所说,MainWindow
第 51 行的方法可以测试负值而不是然后调用 CarTableModel.getValueAt
,但是如果 getValueAt
是从多个调用然后在方法本身中进行参数验证是有意义的。
我正在做一个 Swing 项目。可能,它太大而无法粘贴到这里。我什至尝试记录 table.getSelectedRow() 并且它显示了正确的索引。但不知何故,当我按下一个删除按钮时,这导致了在此 class 中调用的删除方法,selectedRow 更改为 -1,我得到了一个 IndexOutOfBoundsException。 请帮忙。这是 CarTableModelClass:
import javax.swing.table.AbstractTableModel;
import java.util.LinkedList;
public class CarTableModel extends AbstractTableModel {
public LinkedList<Car> cars=new LinkedList<Car>();
@Override
public int getRowCount() {
return cars.size();
}
@Override
public int getColumnCount() {
return 4;
}
@Override
public Object getValueAt(int row, int column){
if((row>cars.size()-1) || (column>3) ){
return null;
}
else {
Car targetCar=cars.get(row);
switch (column){
case 0: {return targetCar.brand;}
case 1: {return targetCar.year;}
case 2: { return targetCar.volume;}
case 3: {return targetCar.maxSpeed;}
default: {return null; }
}
}
}
@Override
public Class<?> getColumnClass(int columnIndex){
switch (columnIndex){
case 0: {return String.class;}
case 1: {return Integer.class;}
case 2: { return Double.class;}
case 3: {return Double.class;}
default: {return Object.class; }
}
}
@Override
public String getColumnName(int columnIndex){
switch (columnIndex){
case 0: {return "Brand";}
case 1: {return "Year";}
case 2: { return "Volume";}
case 3: {return "Max Speed";}
default: {return null; }
}
}
@Override
public boolean isCellEditable(int rowIndex, int columnIndex){
return false;
}
public void addRow(Car value)
{
if(value!=null) {
cars.add(value);
fireTableDataChanged();
}
}
public void update(int index, Car car){
if((car!=null) &&(index>=0)&& (index<(cars.size()-1))){
cars.set(index,car);
fireTableRowsUpdated(index,index+1);
}
}
public void remove(int index){
if((cars!=null) &&(index>=0)&& (index<(cars.size()-1))){
cars.remove(index);
fireTableRowsDeleted(index,index+1);
}
}
}
这里是我得到的例外情况:
Exception in thread "AWT-EventQueue-0" java.lang.IndexOutOfBoundsException: Index: -1, Size: 10
at java.util.LinkedList.checkElementIndex(LinkedList.java:555)
at java.util.LinkedList.get(LinkedList.java:476)
at CarTableModel.getValueAt(CarTableModel.java:26)
at MainWindow.lambda$new[=12=](MainWindow.java:51)
at javax.swing.DefaultListSelectionModel.fireValueChanged(DefaultListSelectionModel.java:184)
at javax.swing.DefaultListSelectionModel.fireValueChanged(DefaultListSelectionModel.java:164)
at javax.swing.DefaultListSelectionModel.fireValueChanged(DefaultListSelectionModel.java:211)
at javax.swing.DefaultListSelectionModel.removeIndexInterval(DefaultListSelectionModel.java:677)
at javax.swing.JTable.tableRowsDeleted(JTable.java:4509)
at javax.swing.JTable.tableChanged(JTable.java:4412)
at javax.swing.table.AbstractTableModel.fireTableChanged(AbstractTableModel.java:296)
at javax.swing.table.AbstractTableModel.fireTableRowsDeleted(AbstractTableModel.java:261)
at CarTableModel.remove(CarTableModel.java:83)
at Toolbar.actionPerformed(Toolbar.java:45)
at javax.swing.AbstractButton.fireActionPerformed(AbstractButton.java:2022)
at javax.swing.AbstractButton$Handler.actionPerformed(AbstractButton.java:2348)
at javax.swing.DefaultButtonModel.fireActionPerformed(DefaultButtonModel.java:402)
at javax.swing.DefaultButtonModel.setPressed(DefaultButtonModel.java:259)
at javax.swing.plaf.basic.BasicButtonListener.mouseReleased(BasicButtonListener.java:252)
at java.awt.Component.processMouseEvent(Component.java:6535)
at javax.swing.JComponent.processMouseEvent(JComponent.java:3324)
at java.awt.Component.processEvent(Component.java:6300)
at java.awt.Container.processEvent(Container.java:2236)
at java.awt.Component.dispatchEventImpl(Component.java:4891)
at java.awt.Container.dispatchEventImpl(Container.java:2294)
at java.awt.Component.dispatchEvent(Component.java:4713)
at java.awt.LightweightDispatcher.retargetMouseEvent(Container.java:4888)
at java.awt.LightweightDispatcher.processMouseEvent(Container.java:4525)
at java.awt.LightweightDispatcher.dispatchEvent(Container.java:4466)
at java.awt.Container.dispatchEventImpl(Container.java:2280)
at java.awt.Window.dispatchEventImpl(Window.java:2750)
at java.awt.Component.dispatchEvent(Component.java:4713)
at java.awt.EventQueue.dispatchEventImpl(EventQueue.java:758)
at java.awt.EventQueue.access0(EventQueue.java:97)
at java.awt.EventQueue.run(EventQueue.java:709)
at java.awt.EventQueue.run(EventQueue.java:703)
at java.security.AccessController.doPrivileged(Native Method)
at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:76)
at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:86)
at java.awt.EventQueue.run(EventQueue.java:731)
at java.awt.EventQueue.run(EventQueue.java:729)
at java.security.AccessController.doPrivileged(Native Method)
at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:76)
at java.awt.EventQueue.dispatchEvent(EventQueue.java:728)
at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:201)
at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:116)
at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:105)
at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:101)
at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:93)
at java.awt.EventDispatchThread.run(EventDispatchThread.java:82)
-1
UPD:这是第 51 行的 lambda:
table.getSelectionModel().addListSelectionListener((event)->
{
int row=table.getSelectedRow();
formPanel.setSelectedRow(row);
toolbar.setSelectedRow(row);
System.out.println(row);
formPanel.fill(
model.getValueAt(row,0),
model.getValueAt(row,1),
model.getValueAt(row,2),
model.getValueAt(row,3)
);
});
问题是,我无法阻止它返回 -1。
看起来该行已被 CarTableModel.remove
成功删除,但这会调用 fireTableRowsDeleted
,后者又会调用 MainWindow
中的某个方法,然后调用 CarTableModel.getValueAt
,但由于该行已被删除,它会引发异常。您已经测试过太大的行或列的值,然后从该方法中测试 return 而不做任何事情。如果您还测试负值,是否一切正常?
或者,正如@JBNeizet 所说,MainWindow
第 51 行的方法可以测试负值而不是然后调用 CarTableModel.getValueAt
,但是如果 getValueAt
是从多个调用然后在方法本身中进行参数验证是有意义的。