自定义实现的ArrayList以及自定义实现的Iterator迭代器
ArrayList的底层是长度可动态变化的数组,其适用于查找多,修改少的情况,原因是数组的元素的增加删除元素会涉及大量元素的移动,效率比较低,ArrayList中的元素可以重复,与插入时的顺序相同,可以为null,继承自AbstractList,对Collection接口中的部分方法做了实现,实现了List接口,List接口中的方法都需要在ArrayList中进行实现,实现了RandomAccess、Cloneable、java.io.Serializable可以实现克隆,可以实现序列化、反序列化。
首先创建一个类,创建一个数组和size属性。
private Object[] elementData;
private int size; public MyArrayLIst(){
this(5);
}
//初始化
public MyArrayLIst(int size) {
this.elementData = new Object[size];
this.size = 0;
}
获取ArrayList的元素个数:
/**
* 获取元素个数
*/
public int size() {
return size;
}
添加元素:涉及到当前的数组是否满需要扩容的情况,即满则扩容
/**
* 添加元素
*/
public boolean add(T value) {
//满则扩容
if (size == elementData.length) {
elementData = Arrays.copyOf(elementData, elementData.length * 2);
}
elementData[size] = value;
size++;
return true;
}
通过下标获取某个元素:应该判断其参数的合法性
/**
* 获取元素
*/
public T get(int index) {
T data = (T) new Object();
if (index >= size || index < 0) {
throw new RuntimeException("参数不合法");
} else {
data = (T) elementData[index];
}
return data;
}
删除元素:删除元素涉及到元素的移动,便需要将删除元素的后面所有元素向前移动
/**
* 删除元素
*/
public boolean remove(int index) {
if (index >= size || index < 0) {
throw new RuntimeException("参数不合法");
} else {
for (int i = index; i < size; i++) {
//元素的移动
elementData[i] = elementData[i + 1];
}
elementData[size - 1] = null;//便于GC的回收
size--;
} return true;
}
要实现Iterator的接口,便需要自定义的ArrayList实现Iterable接口 ,重写他的Iterator方法,实现一个内部类并且重写Iterator的接口,其中包含三个主要的方法
boolean hasNext()
判断 iterator 内是否存在下1个元素,如果存在,返回true,否则返回false。
Object next()
返回 iterator 内下1个元素,同时上面的指针向后移动一位。
故,如果不断地循环执行next()方法,就可以遍历容器内所有的元素了。
void remove()
删除 iterator 内指针的前1个元素,前提是至少执行过1次next();
(这个方法不建议使用,建议使用容器本身的romove 方法)。
@Override
public Iterator<T> iterator() {
return new str();
}
由于其返回的是一个对象,便需要创建一个内部类,来实现其中的方法,代码如下:
class str implements Iterator<T>{
int i;
public str(){
i = 0;
}
@Override
public boolean hasNext() { return i++ < size;
} @Override
public T next() {
if(false){
}
return (T)elementData[i-1];
} @Override
public void remove() { }
}
代码改进:
class str implements Iterator<T>{
private int nextIndex;
private int index;
public str(){
nextIndex = 0;
index = -1; //如果初始数组为空 就不用判断一号位置是否有元素
}
@Override
public boolean hasNext() {
return nextIndex < size;
} @Override
public T next() {
int i = nextIndex;
T value = (T)elementData[i];
nextIndex++;
index = i;
return value ; } @Override
public void remove() {
MyArrayLIst.this.remove(index);
nextIndex = index;
index = -1;
}
}
具体的完整代码如下:
import java.util.Arrays;
import java.util.Iterator; public class MyArrayLIst<T> implements Iterable<T>{
private Object[] elementData;
private int size; public MyArrayLIst(){
this(5);
}
//初始化
public MyArrayLIst(int size) {
this.elementData = new Object[size];
this.size = 0;
} /**
* 添加元素
*/
public boolean add(T value) {
//满则扩容
if (size == elementData.length) {
elementData = Arrays.copyOf(elementData, elementData.length * 2);
}
elementData[size] = value;
size++;
return true;
} /**
* 获取元素
*/
public T get(int index) {
T data = (T) new Object();
if (index >= size || index < 0) {
throw new RuntimeException("参数不合法");
} else {
data = (T) elementData[index];
}
return data;
} /**
* 获取元素个数
*/
public int size() {
return size;
} /**
* 删除元素
*/
public boolean remove(int index) {
if (index >= size || index < 0) {
throw new RuntimeException("参数不合法");
} else {
for (int i = index; i < size; i++) {
//元素的移动
elementData[i] = elementData[i + 1];
}
elementData[size - 1] = null;//便于GC的回收
size--;
} return true;
} @Override
public Iterator<T> iterator() {
return new str();
} // class str implements Iterator<T>{
// int i;
// public str(){
// i = 0;
// }
// @Override
// public boolean hasNext() {
//
// return i++ < size;
// }
//
// @Override
// public T next() {
// if(false){
// }
// return (T)elementData[i-1];
// }
//
// @Override
// public void remove() {
//
// }
// }
class str implements Iterator<T>{
private int nextIndex;
private int index;
public str(){
nextIndex = 0;
index = -1; //如果初始数组为空 就不用判断一号位置是否有元素
}
@Override
public boolean hasNext() {
return nextIndex < size;
} @Override
public T next() {
int i = nextIndex;
T value = (T)elementData[i];
nextIndex++;
index = i;
return value ; } @Override
public void remove() {
MyArrayLIst.this.remove(index);
nextIndex = index;
index = -1;
}
} public static void main(String[] args) {
MyArrayLIst<Integer> myArrayLIst = new MyArrayLIst<>();
myArrayLIst.add(9);
myArrayLIst.add(8);
myArrayLIst.add(1);
myArrayLIst.add(2);
myArrayLIst.add(3);
myArrayLIst.add(5); System.out.println(myArrayLIst.size());
System.out.println(myArrayLIst.get(4)); // myArrayLIst.remove(1);
// System.out.println(myArrayLIst.get(1));
Iterator iterator = myArrayLIst.iterator();
while (iterator.hasNext()) {
System.out.print(iterator.next() + " ");
}
}
}
测试如图:
补充:
一个迭代器实例只能使用一次,如果要再次使用迭代器,便要创建一个新的迭代器实例。
自定义实现的ArrayList以及自定义实现的Iterator迭代器的更多相关文章
- java 16 -11 ArrayList存储自定义对象并增强for遍历
需求:ArrayList存储自定义对象并遍历.要求加入泛型,并用增强for遍历. A:迭代器 B:普通for C:增强for LinkedList,Vector,Colleciton,List ...
- Java基础知识强化之集合框架笔记24:ArrayList存储自定义对象并遍历
1. ArrayList存储自定义对象并遍历 2. 代码示例: Student.java,如下: package cn.itcast_01; public class Student { privat ...
- Java基础六(自定义类、ArrayList集合)
今日内容介绍1.自定义类型的定义及使用2.自定义类的内存图3.ArrayList集合的基本功能4.随机点名器案例及库存案例代码优化 ###01引用数据类型_类 * A: 数据类型 * a: java中 ...
- 06_Java基础语法_第6天(自定义类、ArrayList集合)_讲义
今日内容介绍 1.自定义类型的定义及使用 2.自定义类的内存图 3.ArrayList集合的基本功能 4.随机点名器案例及库存案例代码优化 01引用数据类型_类 * A: 数据类型 * a: java ...
- Java基础语法(自定义类、ArrayList集合)
Java基础语法 今日内容介绍 u 自定义类 u ArrayList集合 第1章 引用数据类型(类) 1.1 引用数据类型分类 提到引用数据类型(类),其实我们对它并不陌生,如使用过的Scanner类 ...
- Android自定义视图三:给自定义视图添加“流畅”的动画
这个系列是老外写的,干货!翻译出来一起学习.如有不妥,不吝赐教! Android自定义视图一:扩展现有的视图,添加新的XML属性 Android自定义视图二:如何绘制内容 Android自定义视图三: ...
- 制作自定义背景Button按钮、自定义形状Button的全攻略(转)
在Android开发应用中,默认的Button是由系统渲染和管理大小的.而我们看到的成功的移动应用,都是有着酷炫的外观和使用体验的.因此,我们在开发产品的时候,需要对默认按钮进行美化.在本篇里,笔者结 ...
- 利用NSUserdefaults来存储自定义的NSObject类及自定义类数组
利用NSUserdefaults来存储自定义的NSObject类及自定义类数组 1.利用NSUserdefaults来存储自定义的NSObject类 利用NSUserdefaults也可以来存储及获取 ...
- Hadoop案例(五)过滤日志及自定义日志输出路径(自定义OutputFormat)
过滤日志及自定义日志输出路径(自定义OutputFormat) 1.需求分析 过滤输入的log日志中是否包含xyg (1)包含xyg的网站输出到e:/xyg.log (2)不包含xyg的网站输出到e: ...
随机推荐
- Codeforces Round #172 (Div. 1 + Div. 2)
A. Word Capitalization 模拟. B. Nearest Fraction 枚举. C. Rectangle Puzzle 求出两个矩形的点,套简单多边形的面积交板子. D. Max ...
- 【t093】外星密码
Time Limit: 1 second Memory Limit: 128 MB [问题描述] 有了防护伞,并不能完全避免2012的灾难.地球防卫小队决定去求助外星种族的帮助.经过很长时间的努力,小 ...
- python模块之模块导入
模块的导入 """ 模块的导入使用:模块导入一般都要放在代码的最上面 不同模块的导入顺序: 1 内置模块 2 扩展模块 3 自定义模块 """ ...
- java 内省综合案例和Beanutils工具包
演示用eclipse自动生成 ReflectPoint类的setter和getter方法. 直接new一个PropertyDescriptor对象的方式来让大家了解JavaBean API的价值,先用 ...
- linux flags 参数
记住 kmalloc 原型是: #include <linux/slab.h> void *kmalloc(size_t size, int flags); 给 kmalloc 的第一个参 ...
- PowerShell 使用 WMI 获取信息
在 PowerShell 可以很容易使用 WMI 拿到系统的信息,如果有关注我的网站,就会发现我写了很多通过 WMI 拿到系统的显卡,系统安装的软件等方法,本文告诉大家如果通过 PowerShell ...
- codeforces 1183F 离散化枚举 约数定理
codeforces1183F 有技巧的暴力 传送门:https://codeforces.com/contest/1183/problem/F 题意: 给你n个数,要你从中选出最多三个数,使得三个数 ...
- .Net Core解除文件上传大小限制
一共要修改两处地方: \Startup.cs public void ConfigureServices(IServiceCollection services) { services.AddMvc( ...
- ELK系统分析nginx日志
一.nginx nginx 服务器日志的log_format格式: log_format main '$remote_addr - $remote_user [$time_local] "$ ...
- 使用IDEA创建基于Maven SpringMvc项目
使用IDEA创建基于Maven SpringMvc项目 1.通过程序启动——create project,或者file--New-projec打开New project 2.自定义groupid等信息 ...