文章详情

短信预约-IT技能 免费直播动态提醒

请输入下面的图形验证码

提交验证

短信预约提醒成功

Java如何自定义一个变长数组

2023-07-04 21:53

关注

这篇文章主要介绍“Java如何自定义一个变长数组”的相关知识,小编通过实际案例向大家展示操作过程,操作方法简单快捷,实用性强,希望这篇“Java如何自定义一个变长数组”文章能帮助大家解决问题。

思路分析

主要功能点:

  1. 新建时可以指定容量大小,不指定时使用默认容量大小。

  2. 向数组中追加新元素,当超过容量时应该自动扩容。

  3. 向数组中指定位置添加新元素,需要考虑指定的下标是否越界,同样也需要考虑扩容操作。

  4. 删除末尾的元素,需要考虑缩小容量。

  5. 删除指定位置元素,需要考虑指定的下标是否越界,同样也需要考虑缩小容量。

  6. 修改特定位置的元素,需要考虑指定的下标是否越界。

  7. 以时间复杂度为O ( 1 ) O(1)O(1)获取任意位置的元素,需要考虑指定的下标是否越界。

主要注意点:

  1. 扩容: 这里扩容2倍(ArrayList 是扩容 1.5 倍),扩容时新建一个2倍容量的新数组,然后将旧数组中的元素按顺序拷贝到新数组。

  2. 缩容: 当数组中的元素个数 <= 0.25 * 容量时,自动缩小容量为原来的一半,新建一个容量是原来容量一半的数组,然后将旧数组中的元素按顺序拷贝到新数组。(ArrayList缩小为和当前元素个数一样大)。

  3. 指定位置添加: 需要先将指定位置及后面所有的元素都向后移动一位,将指定位置空出来然后再插入。

  4. 指定位置删除: 先将制定位置删除,然后将后面的所有元素都向前移动一位。

  5. 容量大小: 需要指定容量的最大值,避免OOM的发生。最小值可以指定也可以不指定。

实现代码

public class ResizeableArray<E> {    private static final int MIN_CAPACITY = 10;    private static final int MAX_CAPACITY = Integer.MAX_VALUE - 8;    // 当前实际数据大小    private int size = 0;    // 实际存放元素的数组,容量为 elements.length    private Object[] elements;    public ResizeableArray(){        this(MIN_CAPACITY);    }    public ResizeableArray(int initCapacity){        if(initCapacity < MIN_CAPACITY){            initCapacity = MIN_CAPACITY;        }else if(initCapacity > MAX_CAPACITY){            initCapacity = MAX_CAPACITY;        }        this.elements = new Object[initCapacity];    }    // 数组的特性,根据下标获取元素    public E get(int index){        this.checkIndex(index);        return (E)elements[index];    }    // 添加一个元素到最后    public void add(E element){        if(size == elements.length){            // 需要扩容            this.expandCapacity();        }        elements[size++] = element;    }    // 添加一个元素到指定位置    public void add(int index, E element){        if(index == size){            this.add(element);            return;        }        this.checkIndex(index);        if(size == elements.length){            // 需要扩容            this.expandCapacity();        }        // 需要先将index和之后的所有元素向后移动一位        for(int i = size - 1; i >= index; i--){            elements[i + 1] = elements[i];        }        elements[index] = element;        size++;    }    // 设置下标为index的元素    private void set(int index, E element){        this.checkIndex(index);        elements[index] = element;    }        private void delete(int index){        this.checkIndex(index);        elements[index] = null;        // 如果删除的不是最后一个元素,需要将后续元素往前移动一位        if(index < size - 1){            for(int i = index + 1; i < size; i++){                elements[i - 1] = elements[i];            }        }        size--;        if(size <= 0.25 * elements.length){            this.reduceCapacity();        }    }    private void deleteLast(){        this.delete(size - 1);    }    private void checkIndex(int index){        if(index < 0 || index >= size){            throw new IndexOutOfBoundsException(String.format("Out of bounds at: %s, size is: %d", index, size));        }    }    private void expandCapacity(){        if(MAX_CAPACITY == elements.length){            // 容量达到最大限制,无法扩容。            throw new RuntimeException("The capacity has reached its maximum limit and cannot be expanded.");        }        int newCapacity = Math.min(elements.length << 1, MAX_CAPACITY);        Object[] newElements = new Object[newCapacity];        System.arraycopy(elements, 0, newElements, 0, size);        elements = newElements;    }    private void reduceCapacity(){        if(elements.length == MIN_CAPACITY){            return;        }        int newCapacity = Math.max(elements.length >> 1, MIN_CAPACITY);        Object[] newElements = new Object[newCapacity];        System.arraycopy(elements, 0, newElements, 0, size);        elements = newElements;    }    public static void main(String[] args){        ResizeableArray<Integer> resizeableArray = new ResizeableArray<>();        System.out.printf("初始化后,size为: %d \n", resizeableArray.size);        System.out.printf("初始化后,capacity为: %d \n", resizeableArray.elements.length);        System.out.println();        for(int i = 0; i < 20; i++){            resizeableArray.add(i);        }        System.out.printf("添加20个元素后,size为: %d \n", resizeableArray.size);        System.out.printf("添加20个元素后,capacity为: %d \n", resizeableArray.elements.length);        System.out.printf("添加20个元素后,第5个元素是: %d \n", resizeableArray.get(4));        System.out.println();        resizeableArray.delete(4);        System.out.printf("删除第五个元素后,size为: %d \n", resizeableArray.size);        System.out.printf("删除第五个元素后,capacity为: %d \n", resizeableArray.elements.length);        System.out.printf("删除第五个元素后,第5个元素是: %d\n", resizeableArray.get(4));        System.out.println();        resizeableArray.add(4, 100);        System.out.printf("在第五个位置插入元素后,size为: %d \n", resizeableArray.size);        System.out.printf("在第五个位置插入元素后,capacity为: %d \n", resizeableArray.elements.length);        System.out.printf("在第五个位置插入元素后,第5个元素是: %d\n", resizeableArray.get(4));        System.out.println();        for(int i = 0; i < 15; i++){            resizeableArray.deleteLast();        }        System.out.printf("删除后面15个元素后,size为: %d \n", resizeableArray.size);        System.out.printf("删除后面15个元素后,capacity为: %d \n", resizeableArray.elements.length);        System.out.printf("删除后面15个元素后,第5个元素是: %d\n", resizeableArray.get(4));        System.out.println();        resizeableArray.set(4, 200);        System.out.printf("修改第五个元素后,当前size为: %d \n", resizeableArray.size);        System.out.printf("修改第五个元素后,capacity为: %d \n", resizeableArray.elements.length);        System.out.printf("修改第五个元素后,第5个元素是: %d\n", resizeableArray.get(4));    }}

测试结果

由执行结果可知:

Java如何自定义一个变长数组

关于“Java如何自定义一个变长数组”的内容就介绍到这里了,感谢大家的阅读。如果想了解更多行业相关的知识,可以关注编程网行业资讯频道,小编每天都会为大家更新不同的知识点。

阅读原文内容投诉

免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

软考中级精品资料免费领

  • 历年真题答案解析
  • 备考技巧名师总结
  • 高频考点精准押题
  • 2024年上半年信息系统项目管理师第二批次真题及答案解析(完整版)

    难度     813人已做
    查看
  • 【考后总结】2024年5月26日信息系统项目管理师第2批次考情分析

    难度     354人已做
    查看
  • 【考后总结】2024年5月25日信息系统项目管理师第1批次考情分析

    难度     318人已做
    查看
  • 2024年上半年软考高项第一、二批次真题考点汇总(完整版)

    难度     435人已做
    查看
  • 2024年上半年系统架构设计师考试综合知识真题

    难度     224人已做
    查看

相关文章

发现更多好内容

猜你喜欢

AI推送时光机
位置:首页-资讯-后端开发
咦!没有更多了?去看看其它编程学习网 内容吧
首页课程
资料下载
问答资讯