IndexOutOfBoundException 使用 java.util.Vector
IndexOutOfBoundException using java.util.Vector
我在使用 java.util.Vector
和 java.util.ArrayList.
时遇到问题
我知道向量中将保存多少元素的容量或更好。因此,我使用构造函数 new Vector<?>(int capacity)
的实现初始化了 java.util.List
。
列表初始化后,我使用了方法set(index, value)
,但此调用导致IndexOutOfBoundException
。这很令人困惑,因为我使用构造函数将容量设置为给定值。
以下代码片段显示了问题:
public void calculateSimple(List<Stock> values, int n) {
if (n<=0) {
throw new IllegalArgumentException("N must not be zero or negativ");
}
int max = values.size();
result = new Vector<Double>(max);
System.out.println("Size of result "+result.size());
if (max == 0) {
result.add(0.0);
}
if (max <= n) {
n = max;
}
for (int i = 1; i <= n; i++) {
List<Double> subList = values.subList(max-i-n, max-i);
result.set(result.size()-i, calculateSimpleValue(subList, n));
}
}
我知道我可以使用简单的数组来解决这个问题。我想问一下代码中是否有任何错误,或者我对容量构造函数有一些错误的想象,关于 class Vector
或任何其他 List
实现。
更新
问题是:
是否可以以混合方式使用任何类型的 java.util 数据结构
(数组、动态列表(或任何其他))
capacity
构造函数参数并不意味着这样数量的元素将自动添加到 ArrayList
中。它仅表示将分配的内部缓冲区的初始大小。如果您可以提前估计列表中将包含多少元素以提高性能,则可以使用它。但是您仍然需要将实际元素添加到列表中。您可以使用循环来做到这一点:
for(int i=0; i<max; i++) result.add(0.0);
从 java.util.Vector.set() 方法我可以看到
/**
* Replaces the element at the specified position in this Vector with the
* specified element.
*
* @param index index of the element to replace
* @param element element to be stored at the specified position
* @return the element previously at the specified position
* @throws ArrayIndexOutOfBoundsException if the index is out of range
* ({@code index < 0 || index >= size()})
* @since 1.2
*/
public synchronized E set(int index, E element) {
if (index >= elementCount)
throw new ArrayIndexOutOfBoundsException(index);
E oldValue = elementData(index);
elementData[index] = element;
return oldValue;
}
因此,当您使用 set 方法时,实例化向量时,您的 result.size()-i >= calculateSimpleValue(subList, n)
.Where elementCount = elementdata.length
可能在构造函数中。
如果你想创建一个用一些值初始化的列表,比如 0.0 或空值,这里有一个快速的方法:
ArrayList<Double> list = new ArrayList<>(Collections.nCopies(100, value));
在上面的例子中,你使用子列表方法的地方,如果max=n那么在这种情况下它会导致负值,这也会导致IndexOutOfBoundException
我在使用 java.util.Vector
和 java.util.ArrayList.
时遇到问题
我知道向量中将保存多少元素的容量或更好。因此,我使用构造函数 new Vector<?>(int capacity)
的实现初始化了 java.util.List
。
列表初始化后,我使用了方法set(index, value)
,但此调用导致IndexOutOfBoundException
。这很令人困惑,因为我使用构造函数将容量设置为给定值。
以下代码片段显示了问题:
public void calculateSimple(List<Stock> values, int n) {
if (n<=0) {
throw new IllegalArgumentException("N must not be zero or negativ");
}
int max = values.size();
result = new Vector<Double>(max);
System.out.println("Size of result "+result.size());
if (max == 0) {
result.add(0.0);
}
if (max <= n) {
n = max;
}
for (int i = 1; i <= n; i++) {
List<Double> subList = values.subList(max-i-n, max-i);
result.set(result.size()-i, calculateSimpleValue(subList, n));
}
}
我知道我可以使用简单的数组来解决这个问题。我想问一下代码中是否有任何错误,或者我对容量构造函数有一些错误的想象,关于 class Vector
或任何其他 List
实现。
更新
问题是: 是否可以以混合方式使用任何类型的 java.util 数据结构 (数组、动态列表(或任何其他))
capacity
构造函数参数并不意味着这样数量的元素将自动添加到 ArrayList
中。它仅表示将分配的内部缓冲区的初始大小。如果您可以提前估计列表中将包含多少元素以提高性能,则可以使用它。但是您仍然需要将实际元素添加到列表中。您可以使用循环来做到这一点:
for(int i=0; i<max; i++) result.add(0.0);
从 java.util.Vector.set() 方法我可以看到
/**
* Replaces the element at the specified position in this Vector with the
* specified element.
*
* @param index index of the element to replace
* @param element element to be stored at the specified position
* @return the element previously at the specified position
* @throws ArrayIndexOutOfBoundsException if the index is out of range
* ({@code index < 0 || index >= size()})
* @since 1.2
*/
public synchronized E set(int index, E element) {
if (index >= elementCount)
throw new ArrayIndexOutOfBoundsException(index);
E oldValue = elementData(index);
elementData[index] = element;
return oldValue;
}
因此,当您使用 set 方法时,实例化向量时,您的 result.size()-i >= calculateSimpleValue(subList, n)
.Where elementCount = elementdata.length
可能在构造函数中。
如果你想创建一个用一些值初始化的列表,比如 0.0 或空值,这里有一个快速的方法:
ArrayList<Double> list = new ArrayList<>(Collections.nCopies(100, value));
在上面的例子中,你使用子列表方法的地方,如果max=n那么在这种情况下它会导致负值,这也会导致IndexOutOfBoundException