2 集合
Java集合整体继承关系如上图所示,该结构图没有将map分支展示出来,对于map将在后续进行描述,java中collection是一个经常用到的工具,熟悉其使用和方法都是十分必要的,接下来笔者将会把java中的集合抽丝剥茧的呈现给诸位。
2.1 List接口
2.1.1 List接口的继承关系
List接口的继承关系如下,最上层是Iterable接口,Collection接口继承自顶层接口Iterable,List又继承了Collection。
2.1.2 Iterable接口
源码如下:
package java.lang;
import java.util.Iterator;
import java.util.Objects;
import java.util.Spliterator;
import java.util.Spliterators;
//支持lambda函数接口
import java.util.function.Consumer;
public interface Iterable<T> {
Iterator<T> iterator();
default void forEach(Consumer<? super T> action) {
Objects.requireNonNull(action);
for (T t : this) {
action.accept(t);
}
}
default Spliterator<T> spliterator() {
return Spliterators.spliteratorUnknownSize(iterator(), 0);
}
}
该接口表示是否可以迭代的,并且支持forEach遍历,Java8常常用forEach配合和lambda表达式,该表达式是实现Consumer接口中accept方法的使用。
2.1.3 Collection接口
Collection接口源码:
package java.util;
import java.util.function.Predicate;
import java.util.stream.Stream;
import java.util.stream.StreamSupport;
public interface Collection<E> extends Iterable<E> {
int size();
boolean isEmpty();
boolean contains(Object o);
Iterator<E> iterator();
Object[] toArray();
boolean add(E e);
boolean remove(Object o);
boolean containsAll(Collection<?> c);
boolean removeAll(Collection<?> c);
default boolean removeIf(Predicate<? super E> filter) {
Objects.requireNonNull(filter);
boolean removed = false;
final Iterator<E> each = iterator();
while (each.hasNext()) {
if (filter.test(each.next())) {
each.remove();
removed = true;
}
}
return removed;
}
boolean retainAll(Collection<?> c);
void clear();
int hashCode();
@Override
default Spliterator<E> spliterator() {
return Spliterators.spliterator(this, 0);
}
default Stream<E> stream() {
return StreamSupport.stream(spliterator(), false);
}
default Stream<E> parallelStream() {
return StreamSupport.stream(spliterator(), true);
}
}
可以看到Collection的主要接口方法有:
接口 | 作用 |
int size(); | 集合大小 |
boolean isEmpty(); | 集合是否为空 |
boolean contains(Object o); | 是否包含某元素 |
Iterator iterator() | 迭代 |
Object[] toArray() | 转数组 |
boolean add(E e); | 添加元素 |
boolean remove(Object o) | 移除某元素 |
boolean containsAll(Collection<?> c) | 是否包含另一个集合 |
boolean removeAll(Collection<?> c) | 移除集合所有 |
…
2.1.4 List接口
再来看看List接口,笔者将List中包含Collection的接口移除掉了:
package java.util;
import java.util.function.UnaryOperator;
public interface List<E> extends Collection<E> {
<T> T[] toArray(T[] a);
boolean addAll(Collection<? extends E> c);
boolean addAll(int index, Collection<? extends E> c);
default void replaceAll(UnaryOperator<E> operator) {
Objects.requireNonNull(operator);
final ListIterator<E> li = this.listIterator();
while (li.hasNext()) {
li.set(operator.apply(li.next()));
}
}
default void sort(Comparator<? super E> c) {
Object[] a = this.toArray();
Arrays.sort(a, (Comparator) c);
ListIterator<E> i = this.listIterator();
for (Object e : a) {
i.next();
i.set((E) e);
}
}
boolean equals(Object o);
E get(int index);
E set(int index, E element);
void add(int index, E element);
int indexOf(Object o);
int lastIndexOf(Object o);
ListIterator<E> listIterator();
List<E> subList(int fromIndex, int toIndex);
@Override
default Spliterator<E> spliterator() {
return Spliterators.spliterator(this, Spliterator.ORDERED);
}
}
可以看到List其实比Collection多了添加方法add和addAll查找方法get,indexOf,set等方法,并且支持index下标操作。
2.1.5 Collection与List的区别
a. 从上边可以看出Collection和List最大的区别就是Collection是无序的,不支持索引操作,而List是有序的。Collection没有顺序的概念。
b. List中Iterator为ListIterator。
c. 由a推导List可以进行排序,所以List接口支持使用sort方法。
d. 二者的Spliterator操作方式不一样。
2.1.6 为什么子类接口里重复申明父类接口呢?
官方解释: **在子接口中重复声明父接口是为了方便看文档。**比如在java doc文档里,在List接口里也能看到Collecion声明的相关接口。