容器 - 实现自定义数组【附源码】

(所有源码均在:https://github.com/zongzhec/JavaPractise

目录

概要

目标

源码

功能实现

源码


容器 - 自定义数组【附源码】

概要

学习一个API的最好办法,就是尝试自己写一个。现在我们尝试自己写一个ArrayList,并实现增删查改的功能。

目标

在写功能之前,先把我们调用的方式定义好,并在心中盘算应该得到的结果。(其实就是一种BDD)

显然此次的目标是增删查改,那么先把调用的方式写好,如下。

源码

package zongzhe.java_basic.data_structure;

public class CustomArrayListDemo {

    public static void main(String[] args) {
        MyArrayList myList = new MyArrayList();

        // 增:自定义容器必须可以添加元素
        myList.add("Zongzhe");
        myList.add("Czz");
        myList.add(null);

        // 删:自定义容器必须可以删除元素
        myList.remove(null);

        // 查:自定义容器必须可以查看元素数量
        System.out.println("size: " + myList.size());

        // 查:必须可以以数组的形式返回所有有效元素
        Object[] all = myList.toArray();
        for (Object obj : all) {
            System.out.println("element: " + obj);
        }

        // 查:必须可以返回指定位置的元素
        System.out.println("get(1): " + myList.get(1));

        // 改:自定义容器必须可以修改元素
        myList.set("Czz", "Czzzz");

        // 需要可以查找obj在当前容器中的索引,如果没有,返回-1
        System.out.println("indexOf(): " + myList.indexOf("Czz"));
    }
}

 

功能实现

在知道怎么用之后,剩下的就是把功能补齐了。特别要注意以下几点:

  1. 增 - 容量问题:新加的元素是不是超出了边界?如果是,怎么扩容?
  2. 查 - 边界问题:查找的元素是否越界?如果是,如何处理?
  3. 查 - 空值问题:如果查找的对象是空值怎么办?equals() 方法怎么处理?

源码

package zongzhe.java_basic.data_structure;

import java.util.Arrays;

/**
 * 实现自定义容器
 */
public class MyArrayList {
    private Object[] data; // 不知道装什么对象,所以用Object 来承载
    private int total; // 表示当前容器的大小,用于扩容和其他检查

    public MyArrayList() {
        data = new Object[10]; // 默认初始化大小
    }

    public void add(Object obj) {
        // 先检查容器是否已满
        if (total >= data.length) {
            data = Arrays.copyOf(data, data.length * 2);
        }
        // 填入数据
        data[total++] = obj;
    }

    public void remove(Object obj) {
        // 先查找位置
        int index = indexOf(obj);
        // 删除
        if (index != -1) {
            System.arraycopy(data, index + 1, data, index, total - index - 1);
            data[--total] = null;
        }
    }

    public int size() {
        return total;
    }

    public void set(Object oldObj, Object newObj) {
        int index = indexOf(oldObj);
        if (index != -1) {
            data[index] = newObj;
        }
    }

    public Object[] toArray() {
        return Arrays.copyOf(data, total);
    }

    public Object get(int index) {
        if (index < 0 || index >= total) {
            throw new IndexOutOfBoundsException("index outOfBound: " + index);
        }
        return data[index];
    }

    public int indexOf(Object obj) {
        int index = -1;
        for (int i = 0; i < total; i++) { // 思考:此处的total能不能换成data.length()?
            if ((obj == null && data[i] == null) || (obj.equals(data[i]))) { // null 也是合法元素
                index = i;
                break;
            }
        }
        return index;
    }
}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值