Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/364.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java中的循环异常_Java_Linked List - Fatal编程技术网

Java中的循环异常

Java中的循环异常,java,linked-list,Java,Linked List,我有以下代码来测试链表和数组列表之间的性能: long start = System.currentTimeMillis(); for (int i = 0; i < 1E5; i++) { list.add(i); } for (int i = 0; i < 1E5; i++) { list.remove(i); } long end = System.currentTimeMillis(); System.out.println(type + ":" + (

我有以下代码来测试链表和数组列表之间的性能:

long start = System.currentTimeMillis();
for (int i = 0; i < 1E5; i++) {
    list.add(i);
}

for (int i = 0; i < 1E5; i++) {
    list.remove(i);
}

long end = System.currentTimeMillis();

System.out.println(type + ":" + (end - start));
long start=System.currentTimeMillis();
对于(int i=0;i<1E5;i++){
列表.添加(i);
}
对于(int i=0;i<1E5;i++){
列表。删除(i);
}
long end=System.currentTimeMillis();
System.out.println(type+“:”+(end-start));
但后来我犯了一个错误:

线程“main”java.lang.IndexOutOfBoundsException中的异常:索引: 50000,尺码:50000

我很困惑。所以我打开了我的Visual Studio,并尝试用c做同样的事情:

列表编号=新列表();
对于(int i=0;i<1E5;i++)
{
增加(i);
}
对于(int i=0;i<1E5;i++)
{
删除(i);
}
Console.WriteLine(“完成了”);
它运行得很好。那么,我是不是在java代码上做了一些错误的事情,或者是在这里学习了一些特别的东西!如果我的英文写得不好,很抱歉:(

The
remove(int)
删除给定索引处的项目, 您想调用.NET所做的
remove(Object)

list.add(Integer.valueOf(i));
list.remove(Integer.valueOf(i));

旧答案

移除时,大小会发生变化,最后只有一个元素位于i=0处, 但你正在移除100000-1

for (int i = 0; i < 1E5; i++) {
    list.remove(i);
}
for(int i=0;i<1E5;i++){
列表。删除(i);
}
或者

for (int i = 0; i < 1E5; i++) {
    list.remove(0);
}

for (int i = 0; i < 1E5; i++) {
    list.remove(list.size() - 1);
}

for (int i = 0; i < 100_000; i++) {
    list.remove(i % list.size());
}
for(int i=0;i<1E5;i++){
列表。删除(0);
}
对于(int i=0;i<1E5;i++){
list.remove(list.size()-1);
}
对于(int i=0;i<100_000;i++){
list.remove(i%list.size());
}

在删除循环中,您可以使用
list.removeLast()
list.remove(0)
list.removeFirst()
。当我增大列表时,列表大小会随着从列表中删除元素而减小。因此,您的代码将一直运行到列表的一半,直到第i个元素不存在为止。

在Java中,有两个版本的
list.remove
remove(T)
,它删除给定的对象,无论它在什么索引处出现,以及
remove(int)
它删除了该索引中的任何对象。如果您有一个
列表,这两种方法有些模糊,但是如果您只传递一个
int
,它将使用
remove(int)
,该操作失败,因为在删除了一半列表后,该索引不再存在

    List<Integer> list = new LinkedList<>();
    for (int i = 0; i < 3; i++) {
        list.add(i);
        System.out.println(list);
    }
    for (int i = 0; i < 3; i++) {
        list.remove(i);  // ERROR!
        System.out.println(list);
    }

您的问题是,在相同的时间删除元素时,在固定的数组长度中循环

考虑在删除时使用
while
循环,而不是
for
,如下所示:

List<Integer> numbersArrayList = new ArrayList<Integer>();
List<Integer> numbersLinkedList = new LinkedList<Integer>();

int E5 = 500000;

// For Array List test
double start = System.currentTimeMillis();
for (int i = 0; i < E5; i++) {
    numbersArrayList.add(i);
}
while (!numbersLinkedList.isEmpty()) {
    numbersArrayList.remove(0);
}
double end = System.currentTimeMillis();
System.out.println("Array List: " + (end - start));


// For Linked List test
start = System.currentTimeMillis();
for (int i = 0; i < E5; i++) {
    numbersLinkedList.add(i);
}
while (!numbersLinkedList.isEmpty()) {
    numbersLinkedList.remove(0);
}
end = System.currentTimeMillis();
System.out.println("linked List: " + (end - start));  
List numbersArrayList=new ArrayList();
列表编号LinkedList=新建LinkedList();
int E5=500000;
//用于阵列列表测试
双启动=System.currentTimeMillis();
对于(int i=0;i
如果您真的想通过迭代列表来删除元素,那么您可以按如下操作

List<Integer> list = new LinkedList<>();

for (int i = 0; i < 1000; i++) {
    list.add(i);
}

for (int i = 1000 - 1; i >= 0; i--) {
    list.remove(i);
}
List List=newlinkedlist();
对于(int i=0;i<1000;i++){
列表.添加(i);
}
对于(int i=1000-1;i>=0;i--){
列表。删除(i);
}
我在这里做的是以相反的顺序进行迭代。因此它总是删除最后一个元素,并且永远不会抛出
java.lang.IndexOutOfBoundsException


这适用于
ArrayList
LinkedList

能否将
list
的定义添加到第一个代码部分?第二个代码不是Java。它是什么?C#?@tobias#k是的,它在Java中有两个版本的
list#remove
remove(int-index)
remove(Object o)
。阅读文档:关于性能的更多信息:您确定在应用程序的末尾按顺序添加对象和从开头按顺序删除对象是最相关的用例吗?两个列表实现的相对性能在很大程度上取决于使用模式。奇怪的是,为什么visual studio example对他有用吗?@dimwittedanimal只是一个猜测,但我认为在另一种语言中,
remove
具有不同的语义,例如,删除数字
50000
,而不是索引
50000
处的元素(在Java中,使用
列表
,这有点含糊不清)如果tobias_k是正确的,那么如果他使用
list.remove(Integer.valueOf(i))
@dimwittedanimal remove删除元素,他将得到相同的行为
List<Integer> numbersArrayList = new ArrayList<Integer>();
List<Integer> numbersLinkedList = new LinkedList<Integer>();

int E5 = 500000;

// For Array List test
double start = System.currentTimeMillis();
for (int i = 0; i < E5; i++) {
    numbersArrayList.add(i);
}
while (!numbersLinkedList.isEmpty()) {
    numbersArrayList.remove(0);
}
double end = System.currentTimeMillis();
System.out.println("Array List: " + (end - start));


// For Linked List test
start = System.currentTimeMillis();
for (int i = 0; i < E5; i++) {
    numbersLinkedList.add(i);
}
while (!numbersLinkedList.isEmpty()) {
    numbersLinkedList.remove(0);
}
end = System.currentTimeMillis();
System.out.println("linked List: " + (end - start));  
List<Integer> list = new LinkedList<>();

for (int i = 0; i < 1000; i++) {
    list.add(i);
}

for (int i = 1000 - 1; i >= 0; i--) {
    list.remove(i);
}