集合 :list

集合框架图
在这里插入图片描述

有这个框架可以看出由Collection派生的两个接口List和set,Queue是java提供的队列实现类似于List

List接口

List是有序的Collection,并且允许重复,使用此接口能够精确的控制每个元素插入的位置。用户能够使用索引(元素List中的位置,类似于数组下标)来访问List中的元素,这类似于Java的数组。
实现List接口的常用类有ArrayList、LinkedList、Vector。***

下面分别是ArrayList、LinkedList、Vector的区别和联系

底层实现方式

(1)ArrayList内部用数组来实现(是对数组的升级,是一个动态方法,提供了一些方法可以直接操作);继承AbstractList类;
(2)LinkedList内部采用双向链表实现;继AbstractSequentialList类;
(3)Vector内部用数组实现;继承AbstractList类。

读写扩容机制

(1)ArrayList:底层是一个动态的数组存在扩容说法;在执行插入元素是超过当前数组预定义的最大值时,数组需要扩容,扩容过程需要调用底层System.arraycopy()方法进行大量的数组复制操作;并且是1.5倍扩容;

private void grow(int minCapacity) {
    // overflow-conscious code
    int oldCapacity = elementData.length;
    int newCapacity = oldCapacity + (oldCapacity >> 1);
    if (newCapacity - minCapacity < 0)
        newCapacity = minCapacity;
    if (newCapacity - MAX_ARRAY_SIZE > 0)
        newCapacity = hugeCapacity(minCapacity);
    // minCapacity is usually close to size, so this is a win:
    elementData = Arrays.copyOf(elementData, newCapacity);
}

(2)Vector底层是动态数组存在扩容的说法。对于Vector,默认创建一个大小为10的Object数组,并将capacityIncrement设置为0;当插入元素数组大小不够时,如果capacityIncrement> 0,则将Object数组的大小扩大为现有size+capacityIncrement;如果capacityIncrement<=0,则将Object数组的大小扩大为现有大小的2倍。

private void grow(int minCapacity) {
    // overflow-conscious code
    int oldCapacity = elementData.length;
    int newCapacity = oldCapacity + ((capacityIncrement > 0) ?
                                     capacityIncrement : oldCapacity);
    if (newCapacity - minCapacity < 0)
        newCapacity = minCapacity;
    if (newCapacity - MAX_ARRAY_SIZE > 0)
        newCapacity = hugeCapacity(minCapacity);
    elementData = Arrays.copyOf(elementData, newCapacity);
}

(3)LinkedList:不存在扩容,因为底层是链表结构;

读写效率

(1)ArrayList对元素的增加和删除都会引起数组的内存分配空间动态发生变化。因此,对其进行插入和删除速度较慢,但检索速度很快。在查找元素时要遍历数组,对于非null的元素采取equals的方式寻找。

(2)Vector这点和ArrayList相似。

(3)LinkedList由于基于链表方式存放数据,增加和删除元素的速度较快,但是检索速度比较慢。在插入元素时,须创建一个新的对象,并更新相应元素的前后元素的引用;在查找元素时,需遍历链表;在删除元素时,要遍历链表,找到要删除的元素,然后从链表上将此元素删除即可。

线程安全性

(1)ArrayList、LinkedList为非线程安全;

(2)Vector是基于synchronized实现的线程安全的ArrayList。但是效率没有ArrayList和LinkedList高;

内存空间占用

(1)ArrayList的空间浪费主要体现在list列表结尾会预留一定的容量空间。

(2)Vector和ArrayList一样。

(3)LinkedList的空间花费则体现在它的每一个元素都要需要消耗比ArrayList多的空间(因为要储存直接前驱和直接后驱以及数据)。

数组和链表:

一.数组

数组静态分配内存。

缺点:在内存中,数组是一块连续的区域。数组需要预留空间,每次申请数组之前必须规定数组的大小,如果大小不合理,则可能会浪费内存。而且它对内存空间要求高,必须有足够的连续内存空间。而且数组大小固定,不能动态拓展。

优点:数组利用下标定位,时间复杂度为O(1),数组插入或删除元素的时间复杂度O(n)。

二.链表

链表动态分配内存。

优点:链表在内存中是不连续的,插入删除速度快(因为有next指针指向其下一个节点,通过改变指针的指向可以方便的增加删除元素)。内存利用率高,不会浪费内存(可以使用内存中细小的不连续空间(大于node节点的大小),并且在需要空间的时候才创建空间)。大小没有固定,拓展很灵活。

缺点:不能随机查找,必须从第一个开始遍历,查找效率低。

  • 2
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值