【Java--数据结构】模拟实现ArrayList

欢迎关注个人主页:逸狼


创造不易,可以点点赞吗~

如有错误,欢迎指出~



目录

LIst

顺序表ArrayList

顺序表优点

IList接口

ArrayList中定义要操作的数组

[在MyArrayList中 重写接口方法](#在MyArrayList中 重写接口方法)

新增元素

在指定位置插入元素

pos不合法异常

判断和查找元素

获取和更新元素

删除元素和清空顺序表

获取顺序表的长度和打印顺序表


LIst

List是个接口,并不能直接用来实例化。 如果要使用,必须去实例化List的实现类。在集合框架中,ArrayList和LinkedList都实现了List接口。

  • ArrayList:实现了List接口,底层为动态类型顺序表
  • LinkedList:实现了List接口,底层为双向链表

Java类和接口总览

顺序表ArrayList

顺序表是用一段物理地址连续的存储单元依次存储数据元素的线性结构,一般情况下采用数组存储。在数组上完成 数据的增删查改。

顺序表优点

适合根据下标进行 查找 和 更新的场景

访问速度比较快(在给定下标的情况下可以达到O(1)

下面我们要自己模拟实现一个 顺序表MyArrayList,理解它底层的数据结构原理,方便我们未来更好的使用ArrayList中的方法。

IList接口

package arrayList;

public interface IList {
     // 新增元素,默认在数组最后新增
     void add(int data);
     // 在 pos 位置新增元素
     void add(int pos, int data) ;
     // 判定是否包含某个元素
     boolean contains(int toFind);
     // 查找某个元素对应的位置
     int indexOf(int toFind) ;
     // 获取 pos 位置的元素
     int get(int pos) ;
     //给 pos 位置的元素设为 value
     void set(int pos, int value) ;
     //删除第一次出现的关键字key
     void remove(int toRemove) ;
     // 获取顺序表长度
     int size() ;
     // 清空顺序表
     void clear();
     // 打印顺序表,注意:该方法并不是顺序表中的方法,为了方便看测试结果给出的
     void display() ;

     boolean isFull();
}

ArrayList中定义要操作的数组

package arrayList;

import java.util.Arrays;
//定义顺序表,实现IList 接口
public class MyArrayList implements IList{

    //定义要操作的数组
    public int[]elem;
    public int usedSize;//数组中存储的数据个数

    public MyArrayList(){
        this.elem=new int[10];//表示数组长度是10

    }

在MyArrayList中 重写接口方法

新增元素

    @Override     // 新增元素,默认在数组最后新增
    public void add(int data) {
        //如果满了,要扩容
        if(isFull()){
            //扩容
            elem= Arrays.copyOf(elem,2*elem.length);
        }
        this.elem[usedSize]=data;
        this.usedSize++;
    }

    @Override//用于判断顺序表是否满了
    public boolean isFull() {
        return usedSize==elem.length;
    }

在指定位置插入元素

@Override     // 在 pos 位置新增元素
    public void add(int pos, int data) {
        //插入数据的时候一定要保证插入的位置前面有数据
        try{
            checkPosOfAdd(pos);
        }catch (PosNotLegalException e){
            e.printStackTrace();
        }
        //判断是否满了
        if(isFull()){
            elem= Arrays.copyOf(elem,2*elem.length);
        }
        //移动元素
        for (int i = usedSize-1; i>=pos  ; i--) {
            elem[i+1]=elem[i];
        }
        //插入元素
        elem[pos]=data;
        usedSize++;
    }

    //该方法用来 判断添加元素时 pos是否合法
    private void checkPosOfAdd(int pos){
        if(pos<0||pos>usedSize){
            throw new PosNotLegalException("在pos位置插入元素时Pos位置不合法。。。");//抛出一个异常
        }
    }

pos不合法异常

package arrayList;
//定义一个异常,用于对pos不合法时的报警
public class PosNotLegalException extends RuntimeException{
    public PosNotLegalException(){

    }
    public PosNotLegalException(String msg){
        super(msg);
    }
}

判断和查找元素

    @Override     // 判定是否包含某个元素
    public boolean contains(int toFind) {
        //只需要找usedSize次
        for (int i = 0; i < usedSize; i++) {
            if(elem[i]==toFind){
                return true;
            }
        }
        return false;
    }

    @Override     // 查找某个元素对应的位置
    public int indexOf(int toFind) {
        for (int i = 0; i < usedSize; i++) {
            if(elem[i]==toFind){
                return i;//与上面contains方法的代码一样,只是返回的是下标
            }
        }
        return -1;
    }

获取和更新元素

 //get/set时,判断pos是否合法
    private void checkPosOfGet(int pos)throws PosNotLegalException{
        if(pos<0||pos>=usedSize){
            throw new PosNotLegalException("get/set获取元素的时候pos位置不合法。。。");
        }
    }
    @Override     // 获取 pos 位置的元素
    public int get(int pos) {
        try{
            checkPosOfGet(pos);
        }catch (PosNotLegalException e){
            e.printStackTrace();
        }
        return elem[pos];
    }

    @Override     //给 pos 位置的元素设为 value   更新pos位置的值为value
    public void set(int pos, int value) {
        try{
            checkPosOfGet(pos);
        }catch (PosNotLegalException e){
            e.printStackTrace();
        }
        elem[pos]=value;
    }

删除元素和清空顺序表

 @Override     //删除第一次出现的关键字key
    public void remove(int toRemove) {
        //要查找是否查找要删除的关键字 toRemove
        int pos =indexOf(toRemove);
        if(pos==-1){
            System.out.println("没有要删除的数字!");
            return;
        }
        for (int i = 0; i < usedSize-1; i++) {
            elem[i]=elem[i+1];
        }
        usedSize--;
    }


    @Override     // 清空顺序表
    public void clear() {
        //1.如果是数组元素,直接将usedSize置为0
        //2.如果是引用类型,则置为null
        /*        for (int i = 0; i < usedSize; i++) {
            elem[i]=null;
        }*/
        usedSize=0;//这里是数组


    }

获取顺序表的长度和打印顺序表

@Override     // 获取顺序表长度
    public int size() {
        return usedSize;
    }

    @Override //打印顺序表
    public void display() {
        for (int i = 0; i < usedSize; i++) {
            System.out.print(elem[i]+" ");
        }
        System.out.println();
    }
相关推荐
钱多多_qdd3 分钟前
spring cache源码解析(四)——从@EnableCaching开始来阅读源码
java·spring boot·spring
waicsdn_haha5 分钟前
Java/JDK下载、安装及环境配置超详细教程【Windows10、macOS和Linux图文详解】
java·运维·服务器·开发语言·windows·后端·jdk
_WndProc7 分钟前
C++ 日志输出
开发语言·c++·算法
薄荷故人_9 分钟前
从零开始的C++之旅——红黑树及其实现
数据结构·c++
Q_192849990615 分钟前
基于Spring Boot的摄影器材租赁回收系统
java·spring boot·后端
qq_4335545416 分钟前
C++ 面向对象编程:+号运算符重载,左移运算符重载
开发语言·c++
Code_流苏18 分钟前
VSCode搭建Java开发环境 2024保姆级安装教程(Java环境搭建+VSCode安装+运行测试+背景图设置)
java·ide·vscode·搭建·java开发环境
努力学习编程的伍大侠20 分钟前
基础排序算法
数据结构·c++·算法
数据小爬虫@35 分钟前
如何高效利用Python爬虫按关键字搜索苏宁商品
开发语言·爬虫·python
ZJ_.37 分钟前
WPSJS:让 WPS 办公与 JavaScript 完美联动
开发语言·前端·javascript·vscode·ecmascript·wps