算法 顺序表

算法

顺序表模拟ArrayList的部分实现

package basic.sft;

public interface List {
    //返回线性表中数据元素的个数
    public int size();
    //返回线性表中序号为i的数据元素
    public Object get(int i);
    //如果线性表为空返回true否则返回false
    public boolean isEmpty();
    //如果线性表中包含元素e返回true否则返回false
    public boolean contains(Object e);
    //返回数据元素e在线性表中的序号
    public int indexOf(Object e);
    //将数据元素插入到线性表中i号位置
    public void add(int i,Object e);
    //将数据元素插入到线性表末尾
    public void add(Object e);
    //将数据元素插入到obj之前
    public boolean addBefore(Object obj,Object e);
    //将数据元素e插入到obj之后
    public  boolean addAfter(Object obj,Object e);
    //删除线性表中第一个与e相同的元素
    public boolean remove(Object e);
    //替换线性表中序号为i的数据元素为e,返回原数据元素
    public Object replace(int i,Object e);


}

package basic.sft;

/**
 * 顺序表
 * 底层采用数组但是顺序可以变化
 */

public class ArrayList implements List {

    private Object[] elementData;//底层是一个数组目前还没有确定长度
    private  int size;//不是数组分配的空间而是元素的个数

    public ArrayList(){
        //没有指定长度默认长度是4
        this(4);
    }
    /**
     *
     * @param initalCapacity 数组的初始长度
     */
    public ArrayList(int initalCapacity){
        //给数组分配指定数量的空间
        elementData = new Object[initalCapacity];
        //指定顺序表的元素个数默认是0
        //size =0;

    }
    @Override
    public int size() {
        return size;
    }

    @Override
    public Object get(int i) {
        if(i<0||i>=size){
            throw new RuntimeException("数组索引越界"+i);
        }
        return elementData[i];
    }

    @Override
    public boolean isEmpty() {
        return size==0;
    }

    @Override
    public boolean contains(Object e) {
        return false;
    }

    @Override
    public int indexOf(Object e) {
        int flag = -1;
        for (int i = 0; i <size ; i++) {
            if(elementData[i].equals(e)){
                flag = i;
                break;
            }
        }
        if(flag==-1){
            throw new RuntimeException("列表中没有"+e+"这个元素");
        }

        return flag;
    }

    @Override
    public void add(int i, Object e) {
        //判断i的位置正确性
        if(i<0||i>size){
            throw new RuntimeException("数组索引越界索引不能为"+i);
        }

        //如果数组满了就扩容
        if(size==elementData.length){
            grow();//相当于elementData = Arrays.copyOf(elementData,elementData.length*2);
        }
        //后移i及其后面的元素,从最后一个开始
        for(int j=size;j>i;j--){
            elementData[j]=elementData[j-1];
        }
        //给数组的第i个位置赋值
        elementData[i]=e;
        //数组的元素个数+1
        size++;

    }

    @Override
    public void add(Object e) {
        //如果数组满了就扩容
        if(size==elementData.length){
            grow();//相当于elementData = Arrays.copyOf(elementData,elementData.length*2);
        }
        //给数组赋值
        elementData[size] = e;
        //元素个数+1
        size++;
    }

    private void grow(){
        //新创建一个数组长度是就数组的2倍
        Object [] newArr = new Object[elementData.length*2];
        //把旧数组的元素赋值给新数组
        for (int i = 0; i < size; i++) {
            newArr[i] = elementData[i];
        }
        //elementData指向新数组
        elementData = newArr;
    }

    @Override
    public boolean addBefore(Object obj, Object e) {
        boolean isadd =false;
        for(int i = 0;i<size;i++){
            if(elementData[i].equals(obj)){
                add(i,e);
                isadd = true;
                break;
            }

        }
        if(isadd==false){
            throw new RuntimeException("列表中没有"+obj+"这个元素");
        }

        return isadd;
    }

    @Override
    public boolean addAfter(Object obj, Object e) {
        boolean isadd =false;
        for (int i = 0; i < size; i++) {
            if(elementData[i].equals(obj)){
                //如果数组满了就扩容
                if(size==elementData.length){
                    grow();//相当于elementData = Arrays.copyOf(elementData,elementData.length*2);
                }
                //后移i及其器后面的元素,从最后一个开始
                for(int j=size;j>i+1;j--){
                    elementData[j]=elementData[j-1];
                }
                //给数组的第i个位置赋值
                elementData[i+1]=e;
                //数组的元素个数+1
                size++;
                isadd =true;
            }

        }
        if(isadd==false){
            throw new RuntimeException("列表中没有"+obj+"这个元素");
        }


        return isadd;
    }

    @Override
    public boolean remove(Object e) {
        boolean b =false;
        for (int i = 0; i < size; i++) {
           if(elementData[i].equals(e)){
               for(int j=i;j<size;j++){
                   elementData[j]=elementData[j+1];
               }
               b =true;
               size--;
               break;
           }

        }
        if(b==false){
            throw new RuntimeException("列表中没有"+e+"这个元素");
        }
        return b;
    }

    @Override
    public Object replace(int i, Object e) {
        //判断i的位置正确性
        if(i<0||i>size){
            throw new RuntimeException("数组索引越界索引不能为"+i);
        }
        elementData[i] =e;
        return elementData;
    }

    @Override
    public String toString() {
        if(size==0){
            return "[]";
        }
        StringBuilder sBuilder = new StringBuilder("[");
        for (int i = 0; i < size; i++) {
            if(i!=size-1) {
                sBuilder.append(elementData[i] + ",");
            }
            else{
                sBuilder.append(elementData[i]);
            }
        }

        sBuilder.append("]");
        
        return sBuilder.toString();
    }
}

posted @ 2019-05-29 19:50  键盘敲坏  阅读(181)  评论(0编辑  收藏  举报