迭代器中遍历元素时用到的next()方法的详解

  • Post author:
  • Post category:其他




对使用迭代器时用到的next()方法的详细介绍



前言

在使用集合存储数据后,我们常使用迭代器iterator(或增强for循环,本质上是迭代器)遍历列表,这样让我们可以很方便地取出列表中的数据元素,而使用迭代器遍历列表时必须要用到的一个方法,即next()方法有一些很让初学者感到困惑的地方,本篇文章就迭代器用到的next()方法进行相关的简单的介绍。




例题讲解

下面我们以ArrayList集合为例,通过一个简单的例题,在解题过程中进行相关问题的探讨。


  • 题目要求

创建并存储Person对象,通过ArrayList集合实现,并使用迭代器遍历。


  • 代码实现

关于代码的实现思路及过程我们就不详细讲述了,我们的重点在next()方法的原理探讨。


代码如下

import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;

public class MainTest {

	public static void main(String[] args) {
		List<Person> list = new ArrayList<Person>();
		
		Person p1 = new Person("小张",19);
		Person p2 = new Person("小王",20);
		Person p3 = new Person("小李",21);
		Person p4 = new Person("小红",18);
		
		list.add(p1);
		list.add(p2);
		list.add(p3);
		list.add(p4);
		
		Iterator<Person> iterator = list.iterator();
		
		while(iterator.hasNext()) {
			Person person0 = iterator.next();
			System.out.println(person0.getName()+" "+person0.getAge());
		}
	}

}


控制台输出

小张 19
小王 20
小李 21
小红 18

到目前来看,没有任何问题,但是如果我再次调用next()方法,并输出里面的信息,会发生什么呢?我们将下面的两行代码添加到原程序的末尾,再运行一次看看结果是什么。

Person person1 = iterator.next();
System.out.println(person1.getName()+" "+person1.getAge());


添加代码后的输出

小张 19
小王 20
小李 21
小红 18
Exception in thread "main" java.util.NoSuchElementException
at java.base/java.util.ArrayList$Itr.next(ArrayList.java:970)
at CSDNCode/nextFunction.MainTest.main(MainTest.java:29)

通过输出结果我们可以看到,前面的四个依然正常输出了,但是下面抛出了异常NoSuchElementException,预期之外的元素,也就是访问的元素不存在!这是为什么呢?在这里我们就不单独把next()方法的方法体拿出来介绍了,并且方法体涉及到的东西较多,不容易理解,如果想详细了解next()方法体的可以通过我的另一篇文章《List集合的并发异常追根溯源》中找到next()的源代码,在这里笔者将通过另一个方面把笔者所理解的next()方法原理做简单的介绍。



next()方法通俗讲解(图解)

在这里我们就要提到指针相关的内容了,因为笔者我在理解next()方法时,并没有去具体看它的源代码,而是通过对程序运行结果的分析,自然地就把这个方法的效果与指针联系到一起了,这里只需要大家具备一点点指针相关的知识即可理解接下来的解释。

需要注意的是,next()方法的内部原理并非是指针,在Java中也没有指针这个说法,这里只是为了理解更加方便, 从而用指针做相关的解释。

下面我们通过三步来理解完整的过程

1.

数据存入


在这里插入图片描述

2.

迭代器封装


使用迭代器就相当于把集合内的所有元素都封装起来到一个容器里了,并且这个容器不可被修改,只能被读取。

在这里插入图片描述

3.

next()遍历(

重点

)

  1. 我们假设容器iterator是一个指针p,在程序开始时,这个指针p应该指向的位置是列表首地址的前一个地址;

注意:这里的iterator并不是指整个大的容器iterator,而是指我们在程序中定义的那个变量iterator,可以认为这是大容器中的一个内部指针。

在这里插入图片描述

  1. iterator(即指针)通过调用hasnext()方法,判断下一个地址是否存在元素;

    在这里插入图片描述

  2. 如果下一地址有元素,则iterator(即指针)通过调用next()方法,将该地址的元素值返回给定义的变量,调用next()方法后,

    指针p会自动移向下一元素的地址

    ;当下一地址没有元素(一般以此作为遍历结束的标志),则不能调用next()方法,如果强行调用则会抛出异常(NoSuchElementException);

    在这里插入图片描述

    在这里插入图片描述



总结

关于next()方法的理解主要在于调用next()后,容器iterator(即比喻的那个p指针)发生的变化;每一次调用next()方法,都会做两步操作;




,先把p指针的下一地址的元素返回;




,再把p指针移动到下一位;

并且这两步操作是同时进行的!这个操作与C语言中文件读取函数的操作极其相类似!建议参照那个函数可以更好地理解这里的next()方法。

关于next方法的相关介绍到这里就结束了,如果有疑问的地方欢迎在评论区留言!谢谢观看~



版权声明:本文为qq_49175846原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。