容器与容器遍历
实现一个可以动态添加对象的容器
模拟一个ArrayList类
利用数组的方式进行存储
public class ArrayList {
// 初始化10个空Object
private Object[] objects = new Object[10];
// objects的下一个空位置
private int index = 0;
/**
* 添加对象
* @param object 对象
*/
public void add(Object object) {
// objects装满的场合
if (index == objects.length) {
// 扩大objects存储的个数
Object[] newObjects = new Object[objects.length * 2];
System.arraycopy(objects, 0, newObjects, 0, objects.length);
objects = newObjects;
}
objects[index] = object;
index++;
}
/**
* 返回objects的个数
* @return 个数
*/
public int size() {
return index;
}
}
测试类:
public class Test {
public static void main(String[] args) {
ArrayList list = new ArrayList();
for(int i=0;i<15;i++){
list.add(new Object());
}
System.out.println(list.size());// 结果:15
}
}
再模拟一个LinkedList类
利用链表的方式进行存储
public class LinkedList {
// 头节点
private Node head = null;
// 尾节点
private Node tail = null;
// 链表元素个数
private int size = 0;
/**
* 添加对象
* @param object 对象
*/
public void add(Object object) {
Node n = new Node(object, null);
// 没有节点的场合
if (head == null) {
head = n;
tail = n;
} else {
tail.setNext(n);
tail = n;
}
size++;
}
/**
* 返回objects的个数
* @return 个数
*/
public int size() {
return size;
}
}
节点类Node
public class Node {
/**
* 当前存储的对象
*/
private Object data;
/**
* 指向下一数据节点
*/
private Node next;
public Node(Object data, Node next) {
super();
this.data = data;
this.next = next;
}
public Object getData() {
return data;
}
public void setData(Object data) {
this.data = data;
}
public Node getNext() {
return next;
}
public void setNext(Node next) {
this.next = next;
}
}
测试类:public class Test {
public static void main(String[] args) {
LinkedList list = new LinkedList();
for(int i=0;i<15;i++){
list.add(new Object());
}
System.out.println(list.size());// 结果:15
}
}
考虑容器的可替换性
新建一个Collection接口,声明add和size方法
public interface Collection {
void add(Object object);
int size();
}
使ArrayList和LinkedList都实现Collection接口
public class ArrayList implements Collection
public class LinkedList implements Collection
测试类:
public class Test {
public static void main(String[] args) {
Collection c = new LinkedList();
for(int i=0;i<15;i++){
c.add(new Object());
}
System.out.println(c.size());// 结果:15
}
}
如何遍历
数组的遍历方式
先写一个Cat的实体类,便于测试。
public class Cat {
private int id;
public Cat(int id) {
this.id = id;
}
@Override
public String toString() {
return "Cat:" + id;
}
}
测试类:
public class Test {
public static void main(String[] args) {
Collection c = new ArrayList();
for (int i = 0; i < 15; i++) {
c.add(new Cat(i));
}
System.out.println(c.size());
ArrayList al = (ArrayList) c;
for (int i = 0; i < al.size(); i++) {
// 需要采用数组下标的取值方式
}
}
}
如果是LinkedList链表存储的,那还得重新写一种遍历方式。
统一遍历方式
每个容器应有一个提供遍历的方法,参照JDK的实现,也把这方法声明为 Iterator iterator()。首先创建一个Iterator接口
public interface Iterator {
boolean hasNext();
Object next();
}
hasNext():返回true,表示后面还有要遍历的元素。
next():取得下一元素。
在Collection接口中添加iterator()方法
public interface Collection {
void add(Object object);
int size();
Iterator iterator();
}
实现了Collection接口的容器ArrayList和LinkedList也必须实现iterator()方法。
ArrayList中iterator()方法的实现
public class ArrayList implements Collection {
// 初始化10个空Object
private Object[] objects = new Object[10];
// objects的下一个空位置
private int index = 0;
public void add(Object object) {
// 参照本文之前的内容
}
public int size() {
// 参照本文之前的内容
}
@Override
public Iterator iterator() {
return new ArrayListIterator();
}
/** 遍历的内部类 */
private class ArrayListIterator implements Iterator {
/** 遍历的当前位置 */
private int currentIndex = 0;
@Override
public boolean hasNext() {
// 当前位置大于等于容器的个数的场合,遍历完毕
if (currentIndex >= index) {
return false;
} else {
return true;
}
}
@Override
public Object next() {
Object object = objects[currentIndex];
currentIndex ++;// 取出当前位置的值后,向后移动一位
return object;
}
}
}
public class Test {
public static void main(String[] args) {
Collection c = new ArrayList();
for (int i = 0; i < 15; i++) {
c.add(new Cat(i));
}
System.out.println(c.size());// 15
Iterator it = c.iterator();
while (it.hasNext()) {
System.out.print(it.next() + " ");
// Cat:0 Cat:1 Cat:2 Cat:3 Cat:4 Cat:5 Cat:6 Cat:7 Cat:8 Cat:9 Cat:10 Cat:11 Cat:12 Cat:13 Cat:14
}
}
}
LinkedList中iterator()方法的实现
public class LinkedList implements Collection {
// 头节点
private Node head = null;
// 尾节点
private Node tail = null;
// 链表元素个数
private int size = 0;
public void add(Object object) {
// 参照本文之前的内容
}
public int size() {
// 参照本文之前的内容
}
@Override
public Iterator iterator() {
return new LinkedListIterator();
}
/** 遍历的内部类 */
private class LinkedListIterator implements Iterator {
/** 遍历的当前元素 */
private Node current = head;
/** 遍历的当前位置 */
private int currentIndex = 0;
@Override
public boolean hasNext() {
// 当前位置大于等于容器的个数的场合,遍历完毕
return currentIndex < size;
}
@Override
public Object next() {
Object object = current.getData();
current = current.getNext();// 取出下一个节点,
currentIndex++;// 向后移动一位
return object;
}
}
}
测试类:
public class Test {
public static void main(String[] args) {
Collection c = new LinkedList();
for (int i = 0; i < 15; i++) {
c.add(new Cat(i));
}
System.out.println(c.size());// 15
Iterator it = c.iterator();
while (it.hasNext()) {
System.out.print(it.next() + " ");
// Cat:0 Cat:1 Cat:2 Cat:3 Cat:4 Cat:5 Cat:6 Cat:7 Cat:8 Cat:9 Cat:10 Cat:11 Cat:12 Cat:13 Cat:14
}
}
}