ArrayList是顺序表结构,底层由数组组成,数组直接存取、删除操作复杂的特点使得ArrayList适用于不涉及频繁增删的场景。在之前的学习中,我们掌握了数组长度是有限的,而ArrayList可以存放任意数量的对象,这是通过动态扩容的方式实现的。
1.最简化方式
package cn.GTMStudio.MyConnection;
/**
* 自定义实现一个ArrayList,体会底层原理
* @author henrly
*/
@SuppressWarnings("all")
public class GTMArrayList {
private Object[] elementData;
private int size;
private static final int DEFAULT_CAPACITY=10;
public GTMArrayList() {
this.elementData=new Object[DEFAULT_CAPACITY];
}
public GTMArrayList(int capacity){
this.elementData=new Object[capacity];
}
public void add(Object obj){
elementData[size++]=obj;
}
@Override
public String toString() {
StringBuilder sb=new StringBuilder();
//[a,b,c]
sb.append("[");
for (int i = 0; i <size; i++) {
sb.append(elementData[i]+",");
}
sb.setCharAt(sb.length()-1, ']');
return sb.toString();
}
public static void main(String[] args) {
GTMArrayList a1=new GTMArrayList(20);
a1.add(2);
a1.add(4);
System.out.println(a1);
}
}
2.泛型
package cn.GTMStudio.MyConnection;
@SuppressWarnings("all")
public class GTMArrayList02<E> {
private Object[] elementData;
private int size;
private static final int DEFAULT_CAPACITY=10;
public GTMArrayList02() {
this.elementData=new Object[DEFAULT_CAPACITY];
}
public GTMArrayList02(int capacity){
this.elementData=new Object[capacity];
}
public void add(E obj){
elementData[size++]=obj;
}
@Override
public String toString() {
StringBuilder sb=new StringBuilder();
//[a,b,c]
sb.append("[");
for (int i = 0; i <size; i++) {
sb.append(elementData[i]+",");
}
sb.setCharAt(sb.length()-1, ']');
return sb.toString();
}
}
3. 动态扩容
package cn.GTMStudio.MyConnection;
import java.util.Arrays;
/**
* 增加数组扩容
*
* @author henrly
*/
@SuppressWarnings("all")
public class GTMArrayList03<E> {
private Object[] elementData;
private int size;
private static final int DEFAULT_CAPACITY = 10;
public GTMArrayList03() {
this.elementData = new Object[DEFAULT_CAPACITY];
}
public GTMArrayList03(int capacity) {
this.elementData = new Object[capacity];
}
public void add(E obj) {
//判断是否需要扩容
if (size == elementData.length) {
//扩容操作
Object[] newArray = new Object[elementData.length + (elementData.length >> 1)];
//elementData = Arrays.copyOf(elementData, newArray.length);
System.arraycopy(elementData, 0, newArray, 0, elementData.length);
elementData=newArray;
}
elementData[size++] = obj;
}
@Override
public String toString() {
StringBuilder sb = new StringBuilder();
//[a,b,c]
sb.append("[");
for (int i = 0; i < size; i++) {
sb.append(elementData[i] + ",");
}
sb.setCharAt(sb.length() - 1, ']');
return sb.toString();
}
public static void main(String[] args) {
GTMArrayList03 a1 = new GTMArrayList03(20);
for (int i = 0; i < 40; i++) {
a1.add("liu" + i);
}
System.out.println(a1);
}
}
4. set和get方法
package cn.GTMStudio.MyConnection;
import java.util.Arrays;
/**
* 增加set和get方法
* 增加:数组边界的检查
*
* @author henrly
*/
@SuppressWarnings("all")
public class GTMArrayList04<E> {
private Object[] elementData;
private int size;
private static final int DEFAULT_CAPACITY = 10;
public GTMArrayList04() {
this.elementData = new Object[DEFAULT_CAPACITY];
}
public GTMArrayList04(int capacity) {
if (capacity < 0) {
throw new RuntimeException("容器的容量不能为负数");
} else if (capacity == 0) {
elementData = new Object[DEFAULT_CAPACITY];
} else {
this.elementData = new Object[capacity];
}
}
public void add(E obj) {
//判断是否需要扩容
if (size == elementData.length) {
//扩容操作
Object[] newArray = new Object[elementData.length + (elementData.length >> 1)];
//elementData = Arrays.copyOf(elementData, newArray.length);
System.arraycopy(elementData, 0, newArray, 0, elementData.length);
elementData = newArray;
}
elementData[size++] = obj;
}
@Override
public String toString() {
StringBuilder sb = new StringBuilder();
//[a,b,c]
sb.append("[");
for (int i = 0; i < size; i++) {
sb.append(elementData[i] + ",");
}
sb.setCharAt(sb.length() - 1, ']');
return sb.toString();
}
public E get(int index) {
checkRange(index);
Object elementDatum = elementData[index];
return (E) elementDatum;
}
public void set(E element, int index) {
checkRange(index);
elementData[index] = element;
}
public void checkRange(int index) {
//索引合法检查
if (index < 0 || index > size - 1) {
throw new RuntimeException("索引不合法:" + index);
}
}
public static void main(String[] args) {
GTMArrayList04 a1 = new GTMArrayList04(20);
for (int i = 0; i < 40; i++) {
a1.add("liu" + i);
}
System.out.println(a1);
System.out.println(a1.get(10));
System.out.println(a1.get(40));
}
}
5. remove方法
package cn.GTMStudio.MyConnection;
import java.util.Arrays;
/**
* 增加remove方法
*
* @author henrly
*/
@SuppressWarnings("all")
public class GTMArrayList05<E> {
private Object[] elementData;
private int size;
private static final int DEFAULT_CAPACITY = 10;
public GTMArrayList05() {
this.elementData = new Object[DEFAULT_CAPACITY];
}
public GTMArrayList05(int capacity) {
if (capacity < 0) {
throw new RuntimeException("容器的容量不能为负数");
} else if (capacity == 0) {
elementData = new Object[DEFAULT_CAPACITY];
} else {
this.elementData = new Object[capacity];
}
}
public void add(E obj) {
//判断是否需要扩容
if (size == elementData.length) {
//扩容操作
Object[] newArray = new Object[elementData.length + (elementData.length >> 1)];
//elementData = Arrays.copyOf(elementData, newArray.length);
System.arraycopy(elementData, 0, newArray, 0, elementData.length);
elementData = newArray;
}
elementData[size++] = obj;
}
@Override
public String toString() {
StringBuilder sb = new StringBuilder();
//[a,b,c]
sb.append("[");
for (int i = 0; i < size; i++) {
sb.append(elementData[i] + ",");
}
sb.setCharAt(sb.length() - 1, ']');
return sb.toString();
}
public E get(int index) {
checkRange(index);
Object elementDatum = elementData[index];
return (E) elementDatum;
}
public void set(E element, int index) {
checkRange(index);
elementData[index] = element;
}
public void checkRange(int index) {
//索引合法检查
if (index < 0 || index > size - 1) {
throw new RuntimeException("索引不合法:" + index);
}
}
public void remove(E element) {
//element,将它和所有元素挨个比较,获得第一个比较为true的,返回
for (int i = 0; i < size; i++) {
if (element.equals(get(i))) {
//将该元素从此处移除
remove(i);
}
}
}
public void remove(int index) {
int numMoved = elementData.length - index - 1;
System.arraycopy(elementData, index + 1, elementData, index, numMoved);
elementData[--size]=null;
}
public int size(){
return size;
}
public boolean isEmpty(){
return size==0;
}
public static void main(String[] args) {
GTMArrayList05 a1 = new GTMArrayList05(20);
for (int i = 0; i < 40; i++) {
a1.add("liu" + i);
}
System.out.println(a1);
a1.remove("liu0");
System.out.println(a1);
System.out.println(a1.get(10));
System.out.println(a1.isEmpty());
}
}