前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场

数组

作者头像
幺鹿
发布于 2019-04-18 07:27:52
发布于 2019-04-18 07:27:52
40800
代码可运行
举报
文章被收录于专栏:Java呓语Java呓语
运行总次数:0
代码可运行

数组三大特性


数组是一种线性表数据结构,它使用一组连续的内存空间,来存储一组具有相同类型的数据。

有三个关键词可以辅助我们理解数组,线性表、连续内存空间、相同数据类型

线性表

由零个或多个数据元素组成的有限序列,线性表中的第一个元素无前驱,最后一个元素无后继,其他元素有且只有一个前驱和后继。常见的线性表除了数组,还有链表、队列、栈也是线性表。

有线性表就有非线性表,如:树、堆、图等就是非线性表。

连续内存空间

连续的内存空间,这个存储特性非常重要,它使得硬件对其友好。因为内存空间是连续的,而数组中的每个块的大小又是相等的。所以非常容易推导出公式:数组头存储的物理地址 + 偏移量=指定下标的物理地址。因为直接能够计算出物理地址,因而计算机就无需再寻址可以直接访问内存,因此这个特性也被称为:数组的随机访问特性

我们经常会听到如下结论:数据查询的时间复杂度是O(1),这个结论本身是不太准确的。数组只有在随机访问的情况下,它的时间复杂度才是O(1)。如果是正常的搜索,即使才有性能最优的二分查找,所需的时间复杂度也要O(logn)。

前面讲到了数组连续内存空间带来的益处:提供了随机访问特性。但是有利也有弊,因为要满足数组占用空间的连续性的特性,就需要靠搬迁数据来保证内存空间的连续性

相同的数据类型

这是一个隐性的定义,日常的时候我们几乎不会关注这个点。我们试想一下,如果存储在数组中的数组,包含 int(4)、long(8)、char(2)、byte(1)、double(8)、float(4) 元素的数组,那么计算物理内存地址的时候是多么麻烦的一件事情。

正是因为要去类型一致,所以会存在空间上的浪费。在对内存空间要求高的应用场景下,如:Redis中自建了的ziplist的数据结构,达到了节省空间的目的。

低效的插入删除操作

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
import java.util.Arrays;

public class Test {
    @org.junit.Test
    public void test() {
        Object[] objects = new Object[5];
        for (int i = 0; i < 5; i++) {
            objects[i] = i;
        }
        System.out.println(Arrays.asList(objects));
        // case 1: 标记清除
        objects[1] = null;
        System.out.println(Arrays.asList(objects));
        // case 2: 执行删除
        Object[] newObjects = new Object[4];
        System.arraycopy(objects, 0, newObjects, 0, 1);
        System.arraycopy(objects, 2, newObjects, 1, 3);
        System.out.println(Arrays.asList(newObjects));
    }
}

// [0, 1, 2, 3, 4]
// [0, null, 2, 3, 4]
// [0, 2, 3, 4]

初始化了样本数据:[0, 1, 2, 3, 4],此时我们希望删除数据1,我们可以怎么操作呢?

  • 直接将对应位置的数值置为 null,删除后的数据如:[0, null, 2, 3, 4],对应代码 case 1。
  • 执行删除操作,然后将后面的数据搬迁,最终数据如:[0, 2, 3, 4],对应代码 case 2。

标记清除的本质是使用空间换时间,我们可以通过触发删除执行的频率来调整性能。删除操作,对应了:新数组申请、数据的拷贝、原数据的释放,相比标记清除算法是一个重量级的操作。

ArrayList 能否完全替代数组?

ArrayList 的优势是官方对 数组的封装,它提供了许多实用的功能,比如:搬迁数据、自动扩容等,种种这些都是手写数组比较困扰的事情。

通常我们的应用场景,使用ArrayList是足够的,但这也不表明数组已无用武之地。因为要使用 ArrayList,就必须要满足 ArrayList 使用的条件。那么在破坏 ArrayList 使用的条件的一些例外情况,则是需要使用数组的。

  • ArrayList 使用泛型,不支持基本类型。高性能场景下(包装类型会自动装箱、拆箱),推荐使用原始类型。
  • 高维数组场景下,选择array[0][0][0][0][0][0][1]对比选择list.get(0).get(0).get(0).get(0).get(0).get(0).get(1),感觉数组更加直观一点。
本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2019.04.08 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
暂无评论
推荐阅读
编辑精选文章
换一批
01.数组深入浅出分析
数组的初始化。Java中的数组必须先初始化,然后才能使用。所谓初始化:就是为数组中的数组元素分配内存空间,并为每个数组元素赋值。
杨充
2025/05/22
800
AI_第一部分 数据结构与算法(4.线性表之数组相关)
第四阶段我们进行深度学习(AI),本部分(第一部分)主要是对底层的数据结构与算法部分进行详尽的讲解,通过本部分的学习主要达到以下两方面的效果:
python编程从入门到实践
2019/10/22
4760
AI_第一部分 数据结构与算法(4.线性表之数组相关)
数据结构-线性表(顺序表与链表的基本知识 以及ArrayList 源码分析)
比如:美女和野兽,抽象的事物表示美女:头发长 前凸后翘。。。 可以表示为一个数据单元,野兽也是一个数据单元。
用户3045442
2018/09/11
7890
数据结构-线性表(顺序表与链表的基本知识 以及ArrayList 源码分析)
Java中数组转集合总结
对于Arrays.asList()方法需要注意以下几点: 1.该方法返回的是基于数组的List视图(List view)。所以,这种方式是将数组转换为List的最快的方式。因为返回的只是视图,不需要多余的内存来创建新的List以及复制操作。
joshua317
2022/03/29
8710
Java中数组转集合总结
Java ArrayList 与顺序表:在编程海洋中把握数据结构的关键之锚
在 Java 编程领域,线性表是一种极为基础且关键的数据结构,它犹如大厦的基石,支撑起众多复杂算法与程序功能的实现。线性表,从直观上理解,是由一系列具有相同类型的数据元素按照特定的顺序依次排列而成的集合,其元素之间存在着一对一的线性关系。 1.1线性表的基本特性: (一)有限性 线性表中的元素数量是有限的。无论是空表(不包含任何元素),还是包含大量元素的表,其元素个数总能确定。例如,一个班级的学生名单,无论班级规模大小,学生人数总归是可以明确统计的。 (二)有序性 元素在表中的排列具有确定的顺序。每个元素都有其特定的位置,除了第一个元素无前驱,最后一个元素无后继外,其他元素都有且仅有一个直接前驱和一个直接后继。就像电影院里的座位号,每个座位都有其固定的前后顺序。 (三)同一性 表中的所有元素都属于同一数据类型。这一特性使得对线性表的操作能够具有一致性和规范性。例如,一个存储整数的线性表,其中所有元素都为整型,这样在进行数学运算或数据比较等操作时就可以按照统一的整型规则进行。 1.2线性表在 Java 中的常见实现方式 存储结构 顺序表利用数组来存储线性表中的元素。在 Java 中,可以声明一个数组来容纳这些元素,例如 Object[] data(或指定具体类型如 int[] data 等)。数组在内存中是连续分配空间的,这使得顺序表在随机访问元素时具有极高的效率。通过元素的索引,可以直接计算出其在内存中的存储地址,从而快速获取到该元素,时间复杂度为 O(1)。 操作实现 插入操作:当向顺序表中插入一个元素时,如果插入位置不是在表尾,需要将插入位置之后的所有元素依次向后移动一位,为新元素腾出空间,然后再将新元素放入指定位置。这种移动操作在元素数量较多时可能会耗费较多时间,平均时间复杂度为O(n) ,其中 为线性表的长度。例如,在一个长度为 100 的顺序表中,如果要在第 50 个位置插入一个元素,就需要将第 50 个到第 100 个元素向后移动一位。 删除操作:类似地,删除操作如果不是删除表尾元素,需要将删除位置之后的元素依次向前移动一位,以填补删除元素后留下的空位。其平均时间复杂度也为O(n) 。比如删除一个长度为 80 的顺序表中的第 30 个元素,就需要将第 31 个到第 80 个元素向前移动一位。 查询操作:由于可以直接通过索引访问数组元素,所以查询指定位置元素的时间复杂度为O(1) 。而查询某个特定值的元素时,可能需要遍历整个顺序表,在最坏情况下时间复杂度为O(n) 。例如,在一个存储学生成绩的顺序表中,如果要查找成绩为 90 分的学生,可能需要逐个比较所有学生的成绩。 二:顺序表
学无止尽5
2024/11/29
910
Java ArrayList 与顺序表:在编程海洋中把握数据结构的关键之锚
4.线性表之数组
数组对于每一门编程语言来说都是重要的数据结构之一,当然不同语言对数组的实现及处理也不尽相同。Java 语言中提供的数组是用来存储固定大小的同类型元素。
码哥字节
2020/04/07
3890
数据结构01-数组
数组(Array)是一种线性表数据结构。它用一组连续的内存空间,来存储一组具有相同类型的数据。
WindCoder
2020/01/22
7390
《Java 算法与数据结构》第2章:数组
数组只是个名称,它可以描述一组操作,也可以命名这组操作。数组的数据操作,是通过 idx->val 的方式来处理。它不是具体要求内存上要存储着连续的数据才叫数据,而是说,通过连续的索引 idx,也可以线性访问相邻的数据。
小傅哥
2022/12/12
4370
《Java 算法与数据结构》第2章:数组
数据结构:数组内存模型
在计算机里,所有的数据结构本质上其实都可以归为两类:数组和链表。对于链表,我将会在第03 与第 04 讲中着重讲解。今天我将要和你一起探索数据结构中最基本的知识点——数组(Array)。
码农架构
2021/01/22
8430
数据结构:数组内存模型
这可能是最细的ArrayList详解了!
# 手撕ArrayList源码 > 文章首发于GitHub开源项目: [Java超神之路](https://github.com/shaoxiongdu/java-notes) ## ArrayList 简介 ArrayList 是一个数组列表。它的主要底层实现是`Object`数组,但与 Java 中的数组相比,它的**容量能动态变化**,可看作是一个动态数组结构。特别注意的是,当我们装载的是基本类型的数据 int,long,boolean,short,byte… 的时候,我们只能存储他们对应的包装
程序员阿杜
2021/09/11
9510
深入理解数组
数组是一种基本的线性表数据结构,它用一段连续的内存空间来存储一组具有相同类型的数据。
一行舟
2022/08/25
3320
面经手册 · 第7篇《ArrayList也这么多知识?一个指定位置插入就把谢飞机面晕了!》
说到数据结构基本包括;数组、链表、队列、红黑树等,但当你看到这些数据结构以及想到自己平时的开发,似乎并没有用到过。那么为什么还要学习数据结构?
小傅哥
2020/08/28
3870
面经手册 · 第7篇《ArrayList也这么多知识?一个指定位置插入就把谢飞机面晕了!》
【数据结构】线性表 ( 线性表概念简介 | 顺序存储结构 / 链式存储结构 | 顺序存储结构 - 顺序表 List | 顺序表 ArrayList 源码分析 )
ArrayList 源代码地址 : https://www.androidos.net.cn/android/9.0.0_r8/xref/libcore/ojluni/src/main/java/java/util/ArrayList.java
韩曙亮
2023/10/11
2990
数据结构-数组
数组(Array)是一种线性表数据结构。它用一组连续的内存空间,来存储一组具有相同类型的数据。
acc8226
2022/05/17
3490
数据结构入门(3)顺序表和链表
线性表(linear list)是n个具有相同特性的数据元素的有限序列。 线性表是一种在实际中广泛使 用的数据结构,常见的线性表:顺序表、链表、栈、队列、字符串...
对编程一片赤诚的小吴
2024/03/13
1060
数据结构入门(3)顺序表和链表
线性表及ArrayList/LinkedList源码分析总结
定义:零个或者多个元素的有限序列。 也就是说它得满足以下几个条件:   ①该序列的数据元素是有限的。   ②如果元素有多个,除了第一个和最后一个元素之外,每个元素只有一个前驱元素和一个后驱元素。   ③第一元素没有前驱元素,最后一个元素没有后继元素。   ④序列中的元素数据类型相同。 则这样的数据结构为线性结构。在复杂的线性表中,一个数据元素(对象)可以由若干个数据项组成,组成一张数据表,类似于数据库。
技术zhai
2019/02/15
6640
一文了解数组
数据结构算法入门系列的第二篇,这次介绍下数组, 数组是一个最基础而且常见的数据结构,几乎每种编程语言都有。
kbsc13
2019/10/24
5080
Java顺序表
推荐一个网站给想要了解或者学习人工智能知识的读者,这个网站里内容讲解通俗易懂且风趣幽默,对我帮助很大。我想与大家分享这个宝藏网站,请点击下方链接查看。 https://www.captainbed.cn/f1
鲜于言悠
2024/05/28
1080
Java顺序表
数据结构与算法学习笔记之 从0编号的数组
数组看似简单,但掌握精髓的却没有多少;他既是编程语言中的数据类型,又是最基础的数据结构;
Dawnzhang
2018/10/18
7590
数组与List的互转及原理分析
使用asList得到的是一个固定程度的一个list,对新的list做元素的修改时可以的,但是,如果更改了大小就会报异常.
用针戳左手中指指头
2021/01/29
5980
数组与List的互转及原理分析
相关推荐
01.数组深入浅出分析
更多 >
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
本文部分代码块支持一键运行,欢迎体验
本文部分代码块支持一键运行,欢迎体验