当前位置: 首页 > 知识库问答 >
问题:

Java集合框架中接口方法的实现发生在哪里?

贺功
2023-03-14

虽然我对Java不是很陌生,但以下问题让我非常困惑,以至于我无法克服。我在网上搜索了很多,也找到了一些答案,但并不完全令人满意。谁能帮我消除疑虑吗

我的困惑是:

 1) Vector v = new Vector();  
    v.addElement("A");  
    ........  
    ........  
    Iterator iter = v.iterator();  

问题1:迭代器是一个接口,我们不能实例化或创建接口的对象。那么,我们应该在这里称之为“iter”,它是什么?

问题1.1:迭代器的所有方法(例如next())都由“iter”调用。这些方法在哪里定义?如果这些方法是在向量类的特定内部类中定义的(正如我在web上发现的),迭代器()方法返回什么?我们不能通过对象“v”直接调用这些方法吗?

问题1.2:根据Javadoc:向量实现{Cloneable、Collection、List、RandomAccess、Serializable}
这些都没有实现迭代器。那么向量是如何实现迭代器的呢?

 2) In the declaration:  
    List list = new ArrayList();  

问题1:List是一个接口,ArrayList是一个类。因此,new ArrayList()创建ArrayList的一个实例<这个实例如何应用于“列表”以及它是什么?

谢谢

共有2个答案

戎兴言
2023-03-14

Q1)您可以创建一个实现接口的实例。iter是对必须实现Iterator的对象的引用

问题1.1)它们作为嵌套类实现。你应该可以在源代码中看到这一点。

iterator()返回对Iterator的引用。

对象v不实现迭代器。

问题1.2)

这些都没有实现迭代器。

这就是为什么你不能调用迭代器的任何方法。

那么向量是如何实现迭代器的呢

事实并非如此。AbstractList有一个实现迭代器的嵌套类

Q1)又?

list是对一个对象的引用,该对象必须实现ArrayList所实现的list(或null)

顺便说一句:除非必须,否则我不会使用向量,我会在示例中使用泛型(它们已经存在8年了;)

宋昕
2023-03-14

Re 1)迭代器实际上通常实现为相应集合类的私有内部类。这就是为什么你看不到实际的实现类,只有接口。这很好,因为它的实现细节不是客户关心的。不过,您可以在调试器中检查其真实类型,或者在与JDK安装捆绑在一起的向量的源代码中查找它。

Vector本身不实现Iterator-它只从其iterator方法返回上面提到的内部类的实例。这个内部类实例引用了创建它的Vector实例,并看到了它的内部,这就是为什么它可以遍历它的元素。这就是为什么Iterator模式很有用:它允许您遍历许多不同的集合(或者实际上Iterables),而无需处理它们的实现细节。

Re 2)你的列表就是它看起来的样子:一个ArrayList类的实例。后者实现了列表接口,因此每个数组列表都是一个列表。

List list = new ArrayList();

是习语“程序用于接口,而不是实现”的示例。由于上面声明的list类型是List,因此您可以像使用任何其他List一样使用它,并且您的后续代码不依赖于它的实际实现。因此,如果后来证明不是ArrayList,最好使用例如LinkedListCopyOnWriteArrayList,您只需要更改上面的一行代码,其余代码仍然可以完美地工作。而如果您将list声明为

ArrayList list = new ArrayList();

后来意识到它的类型应该被更改,你至少需要使用list遍历所有代码,并在提到它的地方相应地更改它的类型。此外,一些代码甚至可能使用特定于ArrayList的方法,这些方法在其他实现类中不可用或工作方式不同,这使得更改的成本更高。

 类似资料:
  • 这段代码过滤调用流,然后打印所有大于10的元素。谓词中的测试方法为我们做到了这一点。 但是filter()方法的实际实现在哪里呢?该方法返回的“流”大于10?我不明白。 这个问题在某种程度上也适用于forEach()方法。它如何在流中迭代?因为filter()和forEach()方法在接口流中是抽象的,没有实现。

  • Map接口概述 Map:双列集合类的根接口,用于存储具有键(Key)、值(Value)映射关系的元素,每个元素都包含一对键值,在使用Map集合时可以通过指定的Key找到对应的Value,例如根据一个学生的学号就可以找到对应的学生。Map接口的主要实现类有HashMap和TreeMap。 将键映射到值的对象,一个映射不能包含重复的键,每个键最多只能映射到一个值。其实Map集合中存储的就是键值对。ma

  • 栈 LIFO Stack LinkedList 双向链表,栈的链式实现 队列 Queue接口 PriorityQueue 优先队列 ConcurrentLinkedQueue 支持并发访问的基于链表的队列 插入 add() offer() 删除 remove() poll() 检查 element() peek() 阻塞队列 BlockingQueue ArrayBlockingQueue 顺序阻

  • 1. Set接口概述 一个不包含重复元素的 collection,无序。 哈希表确定元素是否相同 1、 判断的是两个元素的哈希值是否相同。 如果相同,再判断两个对象的内容是否相同。 2、 判断哈希值相同,其实判断的是对象的HashCode方法。判断内容相同,用的是equals方法。 1.1 HashSet类概述 不保证 set 的迭代顺序,特别是它不保证该顺序恒久不变。 HashSet如何保证元素

  • List接口概述 有序的 collection(也称为序列/线性表)。此接口的用户可以对列表中每个元素的插入位置进行精确地控制。用户可以根据元素的整数索引(在列表中的位置)访问元素,并搜索列表中的元素。与 set 不同,列表通常允许重复的元素。 List接口是Collection接口的一个子接口,List集合的特性是:有序,可重复,元素有索引,List接口有三个实现类 ArrayList:底层数据

  • 1. Java类中集合的关系图 2. 集合类概述 在程序中可以通过数组来保存多个对象,但在某些情况下开发人员无法预先确定需要保存对象的个数,此时数组将不再适用,因为数组的长度不可变。例如,要保存一个学校的学生信息,由于不停有新生来报道,同时也有学生毕业离开学校,这时学生的数目就很难确定。为了在程序中可以保存这些数目不确定的对象,JDK中提供了一系列特殊的类,这些类可以存储任意类型的对象,并且长度可