一、思路
1.顺序表不能是空的,如果顺序表是空的就肯定无法删除第一次出现的 key 元素.
2.定义一个key变量来传入要删除的元素,这个元素要求是第一次出现的.
3.删除之前要先找到第一次出现的key的下标.
4.找到位置之后就开始删除.
5.删除过程是从key下标位置的后一个位置开始向前覆盖.
6.覆盖结束后,将元素个数减少一个.
二、图解
以上图示展示出来的 key 所指向的位置就是要删除元素的位置。
下述图片展示出来就是删除之后的效果。
可以看到 45 这个元素原本是在 3 号下标,但是此时指向的却是 2 号下标。这是由于虽然是删除元素,但是为了保证顺序表的结构没有改变,删除操作实际上就是将后面的元素向前覆盖。
覆盖操作:
覆盖操作指的是将 i + 1 位置上的元素赋值给 i 位置上的元素。
首先要删除的元素就是 i 位置,后面一个位置就是 i + 1。
覆盖即是将 i + 1 位置上的元素放到 i 下标位置,此时原先 i 下标位置上的元素就不见了。
如果整个表都是空的,此时是不可能找到要删除的元素的。
三、代码
class EmptyException extends RuntimeException {
public EmptyException() {
//这是一个提示顺序表为空的异常
}
public EmptyException(String massage) {
super(massage);
}
}
// 求顺序表的长度
public int size() {
// 直接返回元素个数
return this.usedSize;
}
//查找 key 元素的位置 - toFind是我要查找的元素
public int indexOf (int toFind) {
//size()方法求的是顺序表的长度
for (int i = 0; i < this.size(); i++) {
//若顺序表存储的是引用数据类型,该怎么比较?要使用 equals()来比较
if (this.elem[i] == toFind) {
return i; //找到了 - 返回下标
}
}
return -1;//没找到 - 返回-1
}
// 删除第一次出现的 key 元素
public void remove(int key) {
// 顺序表不能是空的
if (isEmpty()) {
// 此时顺序表为空
throw new EmptyException("当前顺序表为空!!!");
}
// 调用 indexOf 方法查找 key 的位置
int index = indexOf(key);
// 判断此时 key 的下标是不是负数
if (index == -1) {
System.out.println("没有这个元素!!!");
return;
}
// 循环遍历覆盖要删除的元素
for (int i = index; i < this.usedSize - 1; i++) {
this.elem[i] = this.elem[i + 1];
}
// 顺序表元素个数减少一个
this.usedSize--;
}
public class MyArrayList {
public static void main(String[] args) {
ArrayList arrayList = new ArrayList();
//测试在顺序表末尾插入一个元素的方法
arrayList.add(1);
arrayList.add(2);
arrayList.add(3);
// 测试在顺序表中指定位置插入一个元素
try{
arrayList.add(1, 10);//将1下标的位置插入一个10
}catch (PosWrongfulException e){ //包裹一下可能会抛出的异常
e.printStackTrace();//如果有异常会提示
}
// 输出删除之前的顺序表
arrayList.disPlay();
System.out.println();
// 测试删除第一次出现的 key 元素
arrayList.remove(10);
// 输出删除之后的顺序表
arrayList.disPlay();
}
}
根据结果可以看到此时确实是删除了 10 这个元素。