【问题标题】:Error removing element from JList with DefaultListModel使用 DefaultListModel 从 JList 中删除元素时出错
【发布时间】:2012-07-29 10:34:01
【问题描述】:

我有一个标准的JList,它将在程序运行时更改。为了让生活更轻松,我创建了一个DefaultListModel 并将其分配给JList

JList CharList = new JList();
DefaultListModel CharListModel = new DefaultListModel();

CharList.setModel(CharListModel);

我可以将文件加载到列表中,然后我可以像这样将项目添加到列表中:

File ChFile = new File (CharListFile);
FileReader freeder = new FileReader (ChFile);
BufferedReader breeder = new BufferedReader(freeder);
String line;
while((line=breeder.readLine())!=null)
{
int pos = CharList.getModel().getSize();
CharListModel.add(pos, line);
}
...
...
//and to add items..
int pos = CharList.getModel().getSize();
CharListModel.add(pos, NewCharName);

但是,我需要能够从列表中删除项目,这给我带来了相当大的麻烦!

我尝试了最明显的方法(是的,选择了一个项目,并且我已经检索了该索引处的索引和字符串):

CharListModel.removeElement(CharList.getSelectedValue());

但是,这给了我一个“java.lang.ArrayIndexOutOfBoundsException: -1”错误。

我已经尝试了您可以在下面的代码中看到的所有排列(有些已被注释掉,但您明白了):

DefaultListModel model = (DefaultListModel) CharList.getModel();//CharListModel;
int selectedIndex = CharList.getSelectedIndex();
if (selectedIndex != -1) {
    //model.remove(selectedIndex);
    //model.removeElement(CharList.getSelectedValue());
    //model.removeElementAt(selectedIndex);
}

以及其他一些排列:

CharListModel.removeElementAt(CharList.getSelectedIndex());
//or
CharListModel.remove(CharList.getSelectedIndex());
//or
CharList.remove(SelItemIndex);

在每种情况下,我都会收到相同的“ArrayIndexOutOfBoundsException”错误,即使先前找到的索引没有问题。是的,我知道我刚才说的是“以前”,所以有些东西可能会改变事情,但这是在我尝试删除元素之前直接运行的代码:

int SelItemIndex = CharList.getSelectedIndex();
if(SelItemIndex == -1)
{
    JOptionPane.showMessageDialog(null, "You have to select something!");
    return;
}
String SelItem = CharList.getModel().getElementAt(SelItemIndex).toString();
//Create warning
final JComponent[] inputs = new JComponent[]
{
    new JLabel("<html>Bla Bla " + SelItem + " Are you sure?</html>")
};
int n = JOptionPane.showConfirmDialog( null, inputs,"Deletion Confirmation Warning", JOptionPane.YES_NO_OPTION);
if( n == 1)
{
    //Do not delete
    return;
}

这就是在尝试删除所选元素之前的全部内容。

对于我的生活,我不知道为什么这不起作用!我在这里错过了什么非常愚蠢的东西吗?

令人困惑的更新

JButtonActionPerformed 事件中,我使用了这段代码 - 代码中的 cmets 解释了为什么这会如此混乱!:

DefaultListModel CharListModel = (DefaultListModel)CharList.getModel();
if( CharListModel.contains(CharList.getSelectedValue()) == true)
{
    //Selected item is found
    int selItemIndex = CharListModel.indexOf(CharList.getSelectedValue());
    if(selItemIndex != -1)
    {
        //Selected item index is NOT -1 and is correct
        CharListModel.remove(selItemIndex);
        //Exception in thread "AWT-EventQueue-0" java.lang.ArrayIndexOutOfBoundsException: -1
    }
    else
    {
        //NEVER reached
        JOptionPane.showMessageDialog(null, "OUCH!");
    }
}

如您所见,所选项目的索引直到将其删除为止都是正确的,因此我再次遇到了超出范围的异常。我也在同一个地方尝试过,但结果相同:

CharListModel.removeElement(CharList.getSelectedValue());

更混乱

为了弄清楚发生了什么,我创建了一个新的DefaultListModel,列举了旧的,并将每个名称放入新模型中,除了我想要删除的那个(记住我可以得到索引,对象和文本,我只是不能删除它)。

这已经奏效了,我现在有一个 DefaultListModel,其中包含正确的项目,但是,当我尝试 CharList.setModel(NewModel); 时,我再次遇到了越界异常。

这让我拔掉了头发!任何人都可以提供任何想法尝试吗?

各种解决方案

根本不是一个真正的解决方案,但为了解决这个令人抓狂的问题,我使用了上面列出的方法,我创建了一个列表模型的副本,减去我想要删除的项目,然后简单地捕获异常使用setModel 时,由于更新后的列表模型添加到列表中就好了,后续操作(例如添加项目等)工作正常,直到我再次尝试删除项目!

感谢您提供帮助 - 如果您对如何解决此问题有任何想法,请务必发布!

问候

最大

【问题讨论】:

  • 我知道,这是一个愚蠢的问题,但是,听起来所选项目在模型中不存在(或不能等同于equal)一个值......去弄清楚如何会工作:P
  • 你能多做几件事吗?你能做到CharListModel.contains(CharList.getSelectedItem()) 和/或CharListModel.indexOf(CharList.getSelectedItem()) 看看他们会返回什么
  • 如需尽快获得更好的帮助,请发帖SSCCE
  • @MadProgrammer - 在这两种情况下,我得到了一个在 getSelectedItem() 上找不到的方法。
  • 请学习java命名约定并遵守它们。

标签: java swing


【解决方案1】:

作为参考,我在example 中添加了以下代码。如果它没有帮助,它可能是一个有用的sscce 来更新您的问题。

panel.add(new JButton(new AbstractAction("Remove") {

    @Override
    public void actionPerformed(ActionEvent e) {
        int index = list.getSelectedIndex();
        if (index != -1) {
            model.remove(index);
        }
    }
}));

【讨论】:

  • trashgod,谢谢,但我已经尝试过了 - 它在测试应用程序中有效,但在主应用程序中无效,并且索引从未 == -1 直到我尝试 remove (或另一种选择)。
  • ArrayIndexOutOfBoundsException 的堆栈跟踪中有什么有用的吗?
  • 老实说,我不知道!有很多(这就是为什么我没有在这里发布),但一开始的信息告诉我这是越界异常。
  • 一种方法是以调试 sscce 中类似的故意错误为例。另见An Introduction to Java Stack Traces
  • 感谢垃圾神,我可能会发现自己使用该链接相当多
【解决方案2】:

我遇到了类似的问题。事实证明,错误不是源于删除元素,而是显示列表。实施时

public void valueChanged(ListSelectionEvent e)

更新屏幕列表的方法,确保在设置值之前检查模型是否为空。这就是导致我的情况出现异常的原因。

创建一个列表,从那里删除,然后用列表更新模型也是一种可用的解决方法。

【讨论】:

  • 工作就像一个魅力。原来我的错误实际上是从 valueChanged 调用的,与堆栈跟踪显示的不同。
【解决方案3】:

我也遇到过同样的问题。似乎当从模型中删除项目时,它也会从数组中删除。因此会弄乱数组索引。

作为一种解决方法,我将数组内容移动到一个列表中,并从模​​型中删除列表内容。现在它对我来说很好用。

【讨论】:

    【解决方案4】:

    我有同样的问题,我解决了这个问题:

    按钮操作

    int index = mylist.getSelectedIndex();
    MyObject = (MyObject) mylist.getSelectedValue();
    int Size = mylistmodel.getSize(); 
    if (index >= 0 && MyObject != null && Size > 0) {
        modeloLista.removeElementAt(indice);
    }
    

    还有。

    listValueChanged

    if (list.getSelectedValue() != null) {
        your code..
    } 
    

    【讨论】:

      猜你喜欢
      • 2013-04-06
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-03-06
      • 2012-05-10
      • 1970-01-01
      相关资源
      最近更新 更多