数据结构|顺序表及Java实现

数据结构|顺序表及Java实现

1. 认识线性表和顺序表

线性表(linear list)是n个具有相同特征的数据元素的有限序列。线性表是一种在实际中广泛使用的数据结构,常见的线性表有:顺序表、链表、栈、队列、字符串…
线性表在逻辑上是线性结构的,但是在物理结构上并不一定是连续的。
1.1 顺序表
逻辑上线性,在内存中存储时,也是严格按照逻辑上的次序保存起来的。
1.2 链表
逻辑上线性,在内存中存储时,不保证连续性。
1.2 数组
数组就是一种“不是非常完备”的顺序表。
数组中存在的问题:
a. 无法严格区分容量和已有元素个数;
b. 数组无法做到自行扩容。

long[] array = new long[5];
  • array 中一共可以放5个 long 元素,无法明确得知目前 array 中有多少个有效的元素(容量)。
  • 一直往 array 中放元素,最多只能放5个,再放就会下标越界。

2. 顺序表

2.1 结构及命名

在这里插入图片描述
注意:顺序表中一定要区分两个概念容量(capacity) vs 元素个数(size),线性表的所有下标只和元素个数相关,和容量无关。

2.2 顺序表(ArrayList)的常见方法

  • 增(向容量中添加元素): add
  • 删(从容量中删除元素): remove
  • 查(不修改容量的情况下获取元素): get/ contains/ indexof/ lastIndexof
  • 改(修改个别元素): set
add(element);
add(index,element);
remove(index);
boolean add(element);
get(index);
set(index,element);
boolean contains(element);
int indexof(element);
int lastindexof(element);
void clear();
int size();
boolean isEmpty();

2.3 关于 jdk 中如何组织 ArrayList 类

在这里插入图片描述

哪个可以实例化对象?
只有类(并且不能是抽象类)才可以实例化对象,只有 ArrayList 可以实例化对象。

2.4 如何实例化对象

ArrayList<Integer> list = new ArrayList<>();

a. ArrayList 是一个泛型类 - 元素类型用泛型表示;
b. 使用默认构造方法(无参构造方法),后面 <> 中由于类型推导,可不写。

3. Java 实现自己的 ArrayList 类

定义 MyLIst 接口

public interface MyList {
    boolean add(Integer e);
    void add(int index, Integer e);

    Integer remove(int index);
    boolean remove(Integer e);

    Integer get(int index);
    Integer set(int index, Integer e);

    boolean contains(Integer e);
    int indexOf(Integer e);
    int lastIndexOf(Integer e);

    void clear();
    int size();
    boolean isEmpty();
}

MyArrayList 实现 MyList 接口

import java.util.Arrays;

public class MyArrayList implements MyList{
    private Integer[] array;
    private int size;

    public MyArrayList(){
        array = new Integer[16];
        size = 0;
    }

    // 供内部扩容
    private void ensureCapacity(){
        if (size < array.length){
            return;
        }

        // 进行扩容
        // 1. 找到一个新的房子,一般来说,房子大小按 2 倍进行扩容
        Integer[] newArray = new Integer[array.length * 2];

        // 2.把原来房子中的东西全部搬到新房子中
        for (int i = 0; i < array.length; i++){
            newArray[i] = array[i];
        }

        // 3. 公布新房子的位置
        this.array = newArray;
    }

    @Override
    public boolean add(Integer e) {
        ensureCapacity();
        array[size] = e;
        size++;
        return true;
    }

    @Override
    public void add(int index, Integer e) {
        ensureCapacity();
        if (index < 0 || index > size){
            throw new ArrayIndexOutOfBoundsException("Index:" + index + ", Size:" + size);
        }

        for (int to = size + 1; to > index; to--){
            array[to] = array[to - 1];
        }

        array[index] = e;
        size++;
    }

    @Override
    public Integer remove(int index) {
        if (index < 0 || index >= size){
            throw new ArrayIndexOutOfBoundsException("Index:" + index + ", Size:" + size);
        }
        Integer e = array[index];
        for (int to = index; to < size - 1; to++){
            array[to] = array[to + 1];
        }
        array[size - 1] = null;
        size--;
        return e;
    }

    @Override
    public boolean remove(Integer e) {
        int i = indexOf(e);
        if (i < 0){
            return false;
        }
        remove(i);
        return true;
    }

    @Override
    public Integer get(int index) {
        if (index < 0 || index >= size){
            throw new ArrayIndexOutOfBoundsException("Index:" + index + ", Size:" + size);
        }
        return array[index];
    }

    @Override
    public Integer set(int index, Integer e) {
        if (index < 0 || index >= size){
            throw new ArrayIndexOutOfBoundsException("Index:" + index + ", Size:" + size);
        }
        Integer oldElement = array[index];
        array[index] = e;
        return oldElement;
    }

    @Override
    public boolean contains(Integer e) {
        if (indexOf(e) >= 0){
            return true;
        }
        return false;
    }

    @Override
    public int indexOf(Integer e) {
        for (int i = 0; i < size; i++){
            if (e.equals(array[i])){
                return i;
            }
        }
        return -1;
    }

    @Override
    public int lastIndexOf(Integer e) {
        for (int i = size - 1; i >= 0; i--){
            if (e.equals(array[i])){
                return i;
            }
        }
        return -1;
    }

    @Override
    public void clear() {
        Arrays.fill(array, null);
        size = 0;
    }

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

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

    @Override
    public String toString() {
        Integer[] toShow = Arrays.copyOf(array, size);
        return Arrays.toString(toShow);
    }
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值