• 自定义ArrayList


    ArrayList

    1、ArrayList底层是使用数据实现的存储(动态数组)

    2、数组的特点:数组在内存中是一段连续的空间,每个元素都有一个下标,数组一旦创建,容量是不可以改变的。

    3、根据下标的特性:查询效率较高,而增加和删除元素就会导致数据发生移动(创建新数组,将旧数组中数据拷贝到新数组中),大量的数据在增加或者删除就会很消耗性能

    4、ArrayList是线程不安全的。

    通过ArrayList源码分析

    1、ArrayList的成员变量 elementData,是一个Object类型的数组

    2、size:集合的个数

    3、默认容量 DEFAULT_CAPACITY = 10 ;

    自定义 ArrayList01

    • 构造方法:在不传值的情况下,默认数组的容量是10

    • 构造方法:在给一个容量的前提下,将容器赋给数组

    • 增加方法:将元素添加到数组中

    • toString方法:将集合中的元素进行遍历,循环打印每一个元素

    package com.xw.arrayList;
    
    /**
     * 自定义实现ArrayList
     */
    public class MyArrayList01 {
    
        private Object[] elementData ;
    
        private int size ;
    
        private static final int DEFAULT_CAPACITY = 10 ;
    
        /**
         * 默认值10
         */
        public MyArrayList01(){
            elementData = new Object[10] ;
        }
    
        /**
         * 带容量的构造方法
         * @param capacity
         */
        public MyArrayList01(int capacity){
            elementData = new Object[capacity] ;
        }
    
        /**
         * 添加方法
         * @param object
         */
        public void add(Object object){
            elementData[size++] = object ;
        }
    
        public String toString(){
            StringBuilder sb = new StringBuilder() ;
            sb.append("[");
            for(int i=0;i<size;i++){
                sb.append(elementData[i]).append(",");
            }
            sb.append("]");
            int i = sb.lastIndexOf(",");
            if (i!=-1){
                sb.deleteCharAt(i);
            }
            return sb.toString();
        }
    
        public static void main(String[] args) {
            MyArrayList01 myArrayList01 = new MyArrayList01(20);
    
            myArrayList01.add("abc");
            myArrayList01.add("efg");
            myArrayList01.add("hig");
    
            System.out.println(myArrayList01);
        }
    
    }
    

    自定义 ArrayList02

    • 在第一个的基础上添加泛型
    package com.xw.arrayList;
    
    /**
     * 添加泛型
     * @param <E>
     */
    public class MyArrayList02<E> {
    
        private Object[] elementData ;
        private int size ;
    
        private static final int DEFAULT_CAPACITY = 10 ;
    
        public MyArrayList02(){
            elementData = new Object[10] ;
        }
    
        public MyArrayList02(int capacity){
            elementData = new Object[capacity] ;
        }
    
        /**
         * 添加方法
         * @param e
         */
        public void add(E e){
            elementData[size++] = e ;
        }
    
        public String toString(){
            StringBuilder sb = new StringBuilder() ;
            sb.append("[");
            for(int i=0;i<size;i++){
                sb.append(elementData[i]).append(",");
            }
            sb.append("]");
            int i = sb.lastIndexOf(",");
            if (i!=-1){
                sb.deleteCharAt(i);
            }
            return sb.toString();
        }
    
        public static void main(String[] args) {
            MyArrayList02<String> myArrayList01 = new MyArrayList02<String>(20);
    
            myArrayList01.add("abc");
            myArrayList01.add("efg");
            myArrayList01.add("hig");
    
            System.out.println(myArrayList01);
        }
    }
    

    自定义 ArrayList03

    思考问题:

    1、数组的容量问题,在指定容量之后(20),循环添加操作(21)次,就会出现错误。-> 扩容问题

    2、什么时候扩容?:在集合的 size==数组的长度

    3、怎么扩容,扩多大:可以将新数组的长度 * /(+)操作,对于计算机底层来说,位运算效率是很高的 我们使用 >>(右移1位相当于除2取余) 或者 << (左移1位相当于*2)

    4、其实扩容的本质就是创建新的数组,将旧数组中的数据拷贝到新数组中。

    新增的方法

    1、扩容

    2、设置添加元素,根据指定下标添加元素

    3、根据下标获取元素

    4、增加一些判断操作

    package com.xw.arrayList;
    
    /**
     * 增加get set方法
     * @param <E>
     */
    public class MyArrayList03<E> {
    
        private Object[] elementData ;
        // 长度
        private int size ;
    
        private static final int DEFAULT_CAPACITY = 10 ;
    
        public MyArrayList03(){
            elementData = new Object[10] ;
        }
    
        public MyArrayList03(int capacity){
            if (capacity<=0){
                throw new RuntimeException("容器容量不能为负数");
            }else if (capacity == 0){
                elementData = new Object[DEFAULT_CAPACITY];
            }else {
                elementData = new Object[capacity] ;
            }
        }
    
        /**
         * 添加方法
         * @param e
         */
        public void add(E e){
            // 什么时候扩容
            if (size==elementData.length){
                Object[] newArray = new Object[elementData.length+(elementData.length>>1)];
                System.arraycopy(elementData,0,newArray,0,elementData.length);
                elementData = newArray ;
            }
            elementData[size++] = e ;
        }
    
        /**
         * 获取元素
         * @param index
         */
        public <E> E get(int index){
            if (index<0||index>size-1){ // 10 index 0|0-9
                throw new RuntimeException("索引不合法");
            }
            return (E)elementData[index] ;
        }
    
        /**
         * 设置值
         * @param element
         * @param index
         */
        public void set(E element,int index){
            if (index<0||index>size-1){ // 10 index 0|0-9
                throw new RuntimeException("索引不合法");
            }
            elementData[index] = element ;
        }
    
        /**
         * toString
         * @return
         */
        public String toString(){
            StringBuilder sb = new StringBuilder() ;
            sb.append("[");
            for(int i=0;i<size;i++){
                sb.append(elementData[i]).append(",");
            }
            sb.append("]");
            int i = sb.lastIndexOf(",");
            if (i!=-1){
                sb.deleteCharAt(i);
            }
            return sb.toString();
        }
    
        public static void main(String[] args) {
            MyArrayList03<String> myArrayList01 = new MyArrayList03<String>(20);
    
            for (int i = 0; i < 40; i++) {
                myArrayList01.add("xing"+i);
            }
    
            System.out.println(myArrayList01);
            System.out.println(myArrayList01.get(1).toString());
    
            myArrayList01.set("张三女",10);
            System.out.println(myArrayList01);
    
            myArrayList01.get(40);
            System.out.println(myArrayList01);
        }
    
    }
    

    自定义 ArrayList04

    删除元素操作:

    1、怎么删:本质还是数组的拷贝

     删除元素 -> 数组的拷贝
     a b c d e f index
     a b (c) d e f  index+1
    

    2、如何拷贝:就是从删除掉的那个元素的下标+1的位置开始移动

    • elementData:原数组

    • index+1:从哪开始移动

    • elementData:新数组

    • index:新数组的下标开始移动的索引

    • elementMoved:移动多少

    int elementMoved = elementData.length-1-index; // 计算个数
    System.arraycopy(elementData,index+1,elementData,index,elementMoved);
    

    3、最后一点:数组中最后一个位置空了出来,需要移除,集合的个数需要 --

    4、增加的方法

    • 根据下标删除元素

    • 集合的个数

    • 判断是否为空

    package com.xw.arrayList;
    
    /**
     * 添加remove方法
     * size:获取集合的个数
     * isEmpty:判断集合是否为空
     * @param <E>
     */
    public class MyArrayList04<E> {
    
        private Object[] elementData ;
        // 个数
        private int size ;
    
        private static final int DEFAULT_CAPACITY = 10 ;
    
        public MyArrayList04(){
            elementData = new Object[10] ;
        }
    
        public MyArrayList04(int capacity){
            if (capacity<=0){
                throw new RuntimeException("容器容量不能为负数");
            }else if (capacity == 0){
                elementData = new Object[DEFAULT_CAPACITY];
            }else {
                elementData = new Object[capacity] ;
            }
        }
    
        /**
         * 添加方法
         * @param e
         */
        public void add(E e){
            // 什么时候扩容
            if (size==elementData.length){
                Object[] newArray = new Object[elementData.length+(elementData.length>>1)];
                System.arraycopy(elementData,0,newArray,0,elementData.length);
                elementData = newArray ;
            }
            elementData[size++] = e ;
        }
    
        /**
         * 获取元素
         * @param index
         */
        public <E> E get(int index){
            if (index<0||index>size-1){ // 10 index 0|0-9
                throw new RuntimeException("索引不合法");
            }
            return (E)elementData[index] ;
        }
    
        /**
         * 设置值
         * @param element
         * @param index
         */
        public void set(E element,int index){
            if (index<0||index>size-1){ // 10 index 0|0-9
                throw new RuntimeException("索引不合法");
            }
            elementData[index] = element ;
        }
    
        /**
         * toString
         * @return
         */
        public String toString(){
            StringBuilder sb = new StringBuilder() ;
            sb.append("[");
            for(int i=0;i<size;i++){
                sb.append(elementData[i]).append(",");
            }
            sb.append("]");
            int i = sb.lastIndexOf(",");
            if (i!=-1){
                sb.deleteCharAt(i);
            }
            return sb.toString();
        }
    
        public void removeElement(E element){
            // 循环比较每一个元素
            for (int i=0;i<size;i++){
                if (element.equals(get(i))){
                    remove(i);
                }
            }
        }
    
        public int size(){
            return size ;
        }
    
        public boolean isEmpty(){
            return size==0?true:false;
        }
    
        /**
         * 根据下标删除元素
         * @param index
         */
        public void remove(int index){
            // 删除元素 -> 数组的拷贝
            // a b c d e f index
            // a b d e f  index+1
            int elementMoved = elementData.length-1-index; // 5-2
            if (index>0){
                System.arraycopy(elementData,index+1,elementData,index,elementMoved);
            }
            // 移除最后一个元素
            elementData[size-1] = null ;
            size--;
        }
    
        public static void main(String[] args) {
            MyArrayList04<String> myArrayList01 = new MyArrayList04<String>(20);
    
            for (int i = 0; i < 40; i++) {
                myArrayList01.add("xing"+i);
            }
    
            System.out.println(myArrayList01);
            System.out.println(myArrayList01.get(1).toString());
    
            myArrayList01.set("张三女",10);
            System.out.println(myArrayList01);
    
            myArrayList01.remove(10);
            System.out.println(myArrayList01);
    
            System.out.println(myArrayList01.size());
            System.out.println(myArrayList01.isEmpty());
    
    //        System.out.println(myArrayList01.size-1);
    //        System.out.println(myArrayList01.elementData.length);
        }
    
    }
    

    OK !!!。

    下一篇:自定义LinkedList

    做的不好,多多指教
  • 相关阅读:
    Entity SQL 初入
    ObjectQuery查询及方法
    Entity Framework 的事务 DbTransaction
    Construct Binary Tree from Preorder and Inorder Traversal
    Reverse Linked List
    Best Time to Buy and Sell Stock
    Remove Duplicates from Sorted Array II
    Reverse Integer
    Implement Stack using Queues
    C++中const限定符的应用
  • 原文地址:https://www.cnblogs.com/xingStudy/p/14626825.html
Copyright © 2020-2023  润新知