3

运行(在运行或调试模式下)我的项目时,我收到一个 ArrayIndexOutOfBounds 错误,这是有道理的。什么不是我检查索引是否> = 0,尽管它说索引是-1,但if中的代码仍然运行。

代码:

...
// Contact List
lstContacts = new JList();
lstContacts.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
lstContacts.setPreferredSize(new Dimension(200, 200));
lstContacts.setMinimumSize(new Dimension(50, 50));
_contactList = _dbi.GetContactList();
_selectedIndex = -1; // An int declared earlier
lstContacts.setListData(_contactList.toArray());
lstContacts.addListSelectionListener(new ListSelectionListener()
{
    public void valueChanged(ListSelectionEvent e)
    {

        System.out.println();
        System.out.println("lstContacts.getSelectedIndex: " + lstContacts.getSelectedIndex());
        System.out.println("!e.getValueIsAdjusting: " + (!e.getValueIsAdjusting()));
        System.out.println("getselectedindex > 0:   " + (lstContacts.getSelectedIndex() > 0));
        System.out.println("Both: " + (!e.getValueIsAdjusting() && (lstContacts.getSelectedIndex() > 0)));

        // Filter out mid-actions
        if(!e.getValueIsAdjusting() && (lstContacts.getSelectedIndex() > 0))
        {

            if(pnlDetail.isVisible())
            {
                saveCurrentContact();
            }
            else
            {
                pnlDetail.setVisible(true);
            }

            System.out.println("  Both: " + (!e.getValueIsAdjusting() && (lstContacts.getSelectedIndex() > 0)));
            _selectedIndex = lstContacts.getSelectedIndex();
            System.out.println("  _selectedIndex: " + _selectedIndex);
            System.out.println("  lstContacts.getSelectedIndex: " + lstContacts.getSelectedIndex());
            PersonalContact sc = (PersonalContact)_contactList.get(_selectedIndex); //crashes here
            showContact(sc);
        }
    }
});
...

我首先在列表中插入了三个虚拟联系人。单击一个运行正常,但单击另一个会引发错误。在下面的错误中,我单击了第二个条目。

控制台输出:

...
lstContacts.getSelectedIndex: 2
!e.getValueIsAdjusting: true
getselectedindex > 0:   true
Both: true
Entry ID [2] modified.

lstContacts.getSelectedIndex: -1
!e.getValueIsAdjusting: true
getselectedindex > 0:   false
Both: false
  Both: false
  _selectedIndex: -1
  lstContacts.getSelectedIndex: -1
Exception in thread "AWT-EventQueue-0" java.lang.ArrayIndexOutOfBoundsException: -1
    at java.util.ArrayList.elementData(Unknown Source)
    at java.util.ArrayList.get(Unknown Source)
    at main.ContactPanel$2.valueChanged(ContactPanel.java:203)
    at javax.swing.JList.fireSelectionValueChanged(Unknown Source)
    at javax.swing.JList$ListSelectionHandler.valueChanged(Unknown Source)
        ... [continued]

看起来它运行正确,然后再次运行并崩溃。我错过了什么(可能是显而易见的事情)?感谢您抽出宝贵的时间以及您能提供的任何帮助。

4

2 回答 2

4

很清楚:

两者:false
两者:false
_selectedIndex:-1
lstContacts.getSelectedIndex:-1
线程“AWT-EventQueue-0”中的异常 java.lang.ArrayIndexOutOfBoundsException:-1

选择的索引是 -1 和做的一样:

_contactList.get(-1);

请记住,Java 中几乎所有的集合都需要一个 >= 0 的索引。

我认为您应该修改您的条件,以检查用户是否(或没有)选择了列表中的项目,以便您可以处理错误。就像是:

if(lstContacts.getSelectedIndex() >= 0){
  _selectedIndex = lstContacts.getSelectedIndex();
  PersonalContact sc = (PersonalContact)_contactList.get(_selectedIndex);
  showContact(sc);
}

希望能帮助到你。

快乐编码!

埃弗拉

于 2013-08-20T18:00:12.870 回答
2

正如对您帖子的评论所表明的那样,当您使用 JList.getSelectedIndex() 检查其值时,可能有其他线程正在更新您的列表并取消选择所有内容。您尚未显示所有代码,但稍后您可能正在使用 lstContacts 执行某些操作,以清除列表中的所有选择。

由于您要响应特定事件,因此不要检查列表中选择的值,在多线程环境中,这些值可能会从一个瞬间变为下一个瞬间。而是使用 来检查事件选择的值 ListSelectionEvent.getFirstIndex()),该值对于该事件应该是常量。

您可能会发现 Oracle 的Concurrency In Swing教程很有帮助。

于 2013-08-20T18:18:28.620 回答