在使用ArrayList时出现IndexOutOfBoundsException错误。

huangapple go评论120阅读模式
英文:

Getting an IndexoutofboundException while using an ArrayList

问题

给定一个数字列表,其中除一个元素外,其他所有元素都在列表中多次出现。找出只出现一次的元素。

以下是Java实现:

```java
package competitiveprogramming;
import java.util.*;

public class FindSingleInArray {

    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        System.out.print("输入数组的大小:");
        int size = sc.nextInt();
        System.out.print("输入一个不重复出现的元素:");
        int arr[] = new int[size];
        for (int i = 0; i < size; i++) {
            arr[i] = sc.nextInt();
        }

        List<Integer> no_duplicate_list = new ArrayList<Integer>();

        for (int j : arr) {
            if (!no_duplicate_list.contains(j)) {
                no_duplicate_list.add(j);
            } else {
                no_duplicate_list.remove(new Integer(j));
            }
        }

        System.out.print(no_duplicate_list.get(0));
        sc.close();
    }
}

以下是我收到的错误消息:

Exception in thread "main" java.lang.IndexOutOfBoundsException: Index 2 out of bounds for length 1
	at java.base/jdk.internal.util.Preconditions.outOfBounds(Preconditions.java:64)
	at java.base/jdk.internal.util.Preconditions.outOfBoundsCheckIndex(Preconditions.java:70)
	at java.base/jdk.internal.util.Preconditions.checkIndex(Preconditions.java:248)
	at java.base/java.util.Objects.checkIndex(Objects.java:373)
	at java.base/java.util.ArrayList.remove(ArrayList.java:502)
	at competitiveprogramming/competitiveprogramming.FindSingleInArray.main(FindSingleInArray.java:28)

<details>
<summary>英文:</summary>


Given a list of numbers, such that all but one element occurs more than once in the list. Find the element that occurs only once.

This is Java implementation:

package competitiveprograming;
import java.util.*;

public class FindSingleInArray {

public static void main(String[] args) {
	Scanner sc= new Scanner(System.in);
	System.out.print(&quot;Enter size of array&quot;);
	int size=sc.nextInt();
	System.out.print(&quot;Enter an element where one of the element will not repeat again..&quot;);
	int arr[]= new int[10];
	for(int i=0;i&lt;size;i++)
	{
		arr[i]=sc.nextInt();
	}
	
	List&lt;Integer&gt; no_duplicate_list= new ArrayList&lt;Integer&gt;();
	
	for(int j : arr)
	{
		if(!no_duplicate_list.contains(j))
		{
			no_duplicate_list.add(j);
		}
		else
		{
			no_duplicate_list.remove(j);
		}
	}
	
	System.out.print(no_duplicate_list.get(0));
	sc.close();
}

}

And this is the error message I&#39;m getting:

Exception in thread "main" java.lang.IndexOutOfBoundsException: Index 2 out of bounds for length 1
at java.base/jdk.internal.util.Preconditions.outOfBounds(Preconditions.java:64)
at java.base/jdk.internal.util.Preconditions.outOfBoundsCheckIndex(Preconditions.java:70)
at java.base/jdk.internal.util.Preconditions.checkIndex(Preconditions.java:248)
at java.base/java.util.Objects.checkIndex(Objects.java:373)
at java.base/java.util.ArrayList.remove(ArrayList.java:502)
at competitiveprograming/competitiveprograming.FindSingleInArray.main(FindSingleInArray.java:28)



</details>


# 答案1
**得分**: 2

如果我理解正确的话,您正在尝试找出输入数组中所有未重复的元素。

所以如果这是输入数组:

1 2 2 3 3 3 4

输出应该如下所示:

1 4

但是您的代码会产生以下结果,因为每当数字出现次数是奇数时,它都会再次被添加到“no_duplicate_list”中:

1 3 4

然而,这并不是导致异常的原因。异常的原因是因为您将一个`int j`传递给了`List.remove(int position)`,它尝试移除位置`j`上的元素,而不是值为`j`的元素。
要修复这个问题,您需要在从列表中移除之前将您的`int`强制转换为`Integer`,这样您就在调用`List.remove(Integer object)`。

```java
no_duplicate_list.remove((Integer)j);
英文:

If I understand you correctly, you are trying to find all elements in the input array which were NOT repeated.

So if this is the input array:

1 2 2 3 3 3 4

The output should look like this:

1 4

But your code will produce this because every uneven time the number appears it will add it to the no_duplicate_list again:

1 3 4

This is however not the reason for your exception. The reason for the exception is because you are passing an int j to List.remove(int position) and it tries to remove the element at position j, and not the element with value of j.
To fix this you need to cast your int into Integer before removing it from the list, this way you are calling List.remove(Integer object).

no_duplicate_list.remove((Integer)j);

答案2

得分: 0

你遇到的错误是“IndexOutOfBoundsException”错误。当您尝试读取或更改数组范围之外的内容时,就会出现这种错误。例如:如果您有一个大小为4的数组,并且尝试读取大小之外的任何元素,如arrayName[7],则会出现此错误。

在您的情况下,您的代码出现此错误是因为您调用了no_duplicate_list.remove(j);remove是一个重载函数,既可以接受列表中类型的元素,也可以接受索引。看起来您正在尝试使用第一个版本,但由于您将参数传递为int,它使用了第二个函数。这告诉代码删除列表范围之外的某个位置的元素。

英文:

The error you are getting is a "IndexOutOfBoundsException" error. This comes when you try to read or change something outside the bound of an array. Example: If you have an array of size 4 and you try to read any element beyond the size like arrayName[7], you get this error.

In your case your code makes this error because you call remove no_duplicate_list.remove(j);. Remove is an overloaded function and can both take an element of the type in the list or take an index. It looks like you are trying to use the first one, but because you are passing the argument as an int, it uses the second function. This tells the code to remove an element at a certain position that is out of bounds of the list.

答案3

得分: 0

你的问题在于你调用了 no_duplicate_list.remove(j);,但 j 应该是一个索引而不是一个值。请参阅官方文档

另一个可能出现的未来错误是你的代码逻辑对以下输入的处理:

1, 2, 1, 2

前两个数字将被添加到列表中,但第三个数字 (1) 已经在列表中,所以它将被删除(如果你修复了向 remove() 方法传递值而不是索引的问题)。同样适用于第四个数字 2。结果是一个空列表,而不是包含两个值 1, 2 的列表。

有两种简单的解决方案:

  1. List 更改为 Set,因为它的实现会忽略重复项。
  2. 只需删除删除元素的代码部分。

我的个人建议是选择选项 1,如果你不希望有重复项,那就不要使用 List 对象,而是使用Java已经为你的问题准备好的某些东西。

英文:

Your problem is that you call no_duplicate_list.remove(j); but j is supposed to be an index not a value. See the official docs.

Another possible future bug is the logic of your code on the following input:

1, 2, 1, 2

the first two numbers will be added to the list but the third number (1) is already in the list, so it will be deleted (if you fix the issue with passing index to remove() method instead of value). Same applies to the forth number 2. The result is an empty list instead of list of two values 1, 2.

There are two simple solutions:

  1. Change List to Set which by its implementation ignores duplicates.
  2. Just remove the part of the code of removing the element.

My personal advice is option 1, if you don't want duplicates, just don't use List object and use something that Java has already prepared for your problem.

答案4

得分: 0

IndexOutOfBounds的原因已经解答。实际问题的逻辑是错误的。

以1,1,1,2,2,3为例。最初,1被添加到no_dup,然后在下一步被移除,再在第三次迭代时再次添加1。最终的结果将包含1和3,但理想情况下,答案应该是3。

使用HashMap应该可以快速处理大量输入。

英文:

The reason for IndexOutOfBounds is answered already. The logic for the actual problem is incorrect.

Consider 1,1,1,2,2,3 as an example. Initially, 1 is added to no_dup and then it will be removed next and again 1 will be added in third iteration. The final result will have 1&3, but ideally, the answer should be 3.

Using HashMaps should be quick even if the input is large.

huangapple
  • 本文由 发表于 2020年4月5日 07:27:49
  • 转载请务必保留本文链接:https://go.coder-hub.com/61036116.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定