手写ArrAyList集合(简化版)

重点:

1.扩容技术
2.Arrays.copyOf()和System.arraycopy()这两个API

public class ExtArrayList<E> implements ExtList<E> {
	// 保存ArrayList中数据的数组
	private transient Object[] elementData;
	// ArrayList实际数量
	private int size;

	public ExtArrayList() {
		// 默认初始容量为10
		this(10);
	}

	public ExtArrayList(int initialCapacity) {
		//判断初始容量
		if (initialCapacity < 0) {
			throw new IllegalArgumentException("Illegal Capacity: " + initialCapacity);
		}
		// 初始化数组容量
		elementData = new Object[initialCapacity];
	}

	// 添加方法实现
	public void add(Object object) {		
		ensureExplicitCapacity(size + 1);
		//size++是为了让第0个索引也可以添加到数组
		elementData[size++] = object;
	}
	//添加对象到指定索引
	public void add(int index, Object object) {
		rangeCheck(index);
		ensureExplicitCapacity(size + 1);
		System.arraycopy(elementData, index, elementData, index + 1, size - index);
		elementData[index] = object;
		size++;
	}

	
	// 获取数据
	public Object get(int index) {
		rangeCheck(index);
		return elementData[index];
	}
	//删除方法
	public Object remove(int index) {
		Object object = get(index);
		//获取删除索引后方的长度
		int numMoved = elementData.length - index - 1;
		if (numMoved > 0){			
		  	//这个方法下面有详细介绍														
			System.arraycopy(elementData, index + 1, elementData, index, numMoved);
		}
		elementData[--size] = null;
		return object;
	}

	public boolean remove(E object) {
		for (int i = 0; i < elementData.length; i++) {
			Object element = elementData[i];
			if (element.equals(object)) {
				remove(i);
				return true;
			}
		}
		return false;
	}
	//检查下标是否越界
	private void rangeCheck(int index) {
		if (index >= size) {
			throw new IndexOutOfBoundsException("数组越界啦!");
		}
	}
	//遍历的时候需要使用
	public int getSize() {
		return size;
	}
	//如果存入的数据,超出了默认数组初始容量 就开始实现扩容
	//minCapacity 最小扩容为size+1
	public void ensureExplicitCapacity(int minCapacity) {
		// 如果存入的数据,超出了默认数组初始容量 就开始实现扩容
		if (size == elementData.length) {
			// 获取原来数组的长度 2
			int oldCapacity = elementData.length;
			// oldCapacity >> 1 理解成 oldCapacity/2 新数组的长度是原来长度1.5倍
			int newCapacity = oldCapacity + (oldCapacity >> 1); // 3
			if (newCapacity < minCapacity) {
				// 最小容量比新容量要小的,则采用初始容量minCapacity
				newCapacity = minCapacity;
			}
			// System.out.println("oldCapacity:" + oldCapacity + ",newCapacity:"
			// + newCapacity);
			elementData = Arrays.copyOf(elementData, newCapacity);
		}
	}


		//作用: 拷贝数组,数据源和数据目标不需要是同一个数组,这里只是用到了同一个数组!
		//	elementData : 数据源
		//	index + 1   : 拷贝起始索引,就是从这个数据源的那个索引开始复制

 		//	elementData : 目标数组
		//	index 		: 把从数据源索引复制的数据,从当前数组的那个索引开始存放
 		//	numMoved    : 从源数组拷贝多少条数据过来!

		//作用举例:
 		//	String elementData=["A","B","C","D","E"];
		//	int indea = 1;
		//	numMoved  = 2;
		//	结果为:
		//		elementData["A","C","D","D","E"]
		System.arraycopy(elementData, index + 1, elementData, index, numMoved);
}
思路总结:
  • 新增:

    1. 如果长度不够就使用指定的倍数或者最小扩容size+1数做为新的长度
    2. 使用ArrayOf拷贝原始数组,填入扩容后的长度
  • 删除:
    1.使用System.arraycopy() 手写ArrAyList集合(简化版)_第1张图片

  • 修改:

    1. 覆盖添加
  • 查询:

    1. 通过下标直接获取
  • 总结:

    1.List查询快 直接通过索引可以定位!
    2.增删慢因为修改后是对应index后所有的数据都会变化!
    3.不早了睡觉明天再补充!

你可能感兴趣的:(java基础面试题)