探索Java集合框架—数据结构、ArrayList集合

news2024/9/22 13:24:19

一、背景介绍

Java集合的使用相信大家都已经非常得心应手,但是我们怎么做到知其然,更知其所以然这种出神入化的境界呢?我们揭开集合框架底层神秘面纱来一探究竟

目录

一、背景介绍

二、思路&方案

数据结构是什么?

数据结构可以分为线性和非线性两种数据结构

线性数据结构:

非线性数据结构:

Java集合分类

Collection接口:

Map接口:

三、过程

ArrayList和LinkedList的区别有哪些?

ArrayList是如何存储数据的?

ArrayList扩容机制

①、如何进行扩容的?

②、增加元素

③、ArrayList给指定位置插入元素

④、删除元素

按照下标位置删除元素

按照内容删除元素

四、总结


二、思路&方案

在说集合之前我们要先了解数据结构这一概念

数据结构是什么?

数据结构时对数据进行组织和存储一种方式,数据使用不同的数据结构组织和存储时所带来的时间和空间性能也是不同的。List、Set、Map集合背后使用了不同的数据结构,我们理解为集合是一种数据结构的具体实现。例如:可以使用数组结构来实现集合,当访问数组元素的时候通过数组下标查找时更快。

程序=数据结构+算法。数据结构还提供了一些各种查找、排序算法,集合可以用来解决一堆数据的处理问题,如:查找、排序、去重等等

数据结构可以分为线性和非线性两种数据结构

线性数据结构:

特点:

一对一的关系并且逻辑上有序,数据元素之间存在一个前后关系,每个元素只有一个直接前驱和一个直接后去

组成:

  • 数组(Array):相同类型元素并且连续存储
  • 链表(LinkedList):一系列node节点,每个节点包括数据、指向下一个节点的指针
  • 栈(Stack):先进后出(LIFO),在栈顶进行删除和插入操作
  • 队列(Queue):先进先出(FIFO),在队尾插入、对头删除元素

非线性数据结构:

特点:

多对多关系,数据元素之间不存在直接的前后关系,元素和元素之间通过指针相连,

包括:

  • 树(Tree):一组node节点组成,每个父节点下级可以有子节点,节点之间是上下层次关系
  • 图(Graph):一组节点、边之间的关系
  • 堆(Heap):实现优先队列
  • 散列表(Hash Table):根据关键字可以直接查询数据,通过散列函数确认存储位置

结合上面讲到的数据结构,我们来看下Java究竟是如何应用的


Java集合分类

集合相关类和接口都在java.util中,从宏观上我们把Java集合分为了以Collection为中心的实现类、以Map为中心的实现类, Collection和Map两个接口下面分别有不同的实现类,它们都是用来存储和操作数据的集合

Collection接口:

特点:

一组对象的集合,通过索引或迭代器访问元素,元素可以重复

包括:

  • List:有序集合
  • Set:无序集合
  • Queue:先进先出集合

Map接口:

特点:

键值对映射的集合,通过key查找value,每个key是唯一的

包括:

  • HashMap:通过哈希表实现,无序
  • TreeMap:基于红黑树实现,有序
  • LinkedHashMap:哈希表+双向链表实现,顺序插入

今天先重点来讲讲List集合中ArrayList增删改查是如何实现的



三、过程

ArrayList和LinkedList的区别有哪些?

ArrayList是如何存储数据的?

底层是数组,数组存储的数据的特点是元素类型相同并且数组容量固定

数组存储容量固定?那在实际业务场景中数据肯定是不固定的呀?如何解决?

ArrayList扩容机制

ArrayList提供了自动扩容机制,当插入数据时候底层会先判断是否需要扩容,如果当前容量+1超过数组长度,就会进行扩容,反之。

①、如何进行扩容的?

ArrayList内部封装了一个动态再分配的对象数组,ArrayList的底层数据库初始容量为10,扩容因子为1.5

 

②、增加元素

当我们第一次添加元素使用add()方法添加元素的过程中,底层的流程是这样的:

内部会调用ensureExplicitCapacity()方法判断添加元素之后的数组长度是否大于数组容量,如果超出数组容量调用grow()方法扩容,否则给数组长度+1

当第一次对数组进行add添加元素的时候,才会把内部的数组扩容为10,这也是数组的第一次扩容

 注意:

  • 数组长度是指当前数组内元素的个数
  • 数组容量是指数组所能容纳的长度

示意图:

那如果要添加的元素不足数组容量呢?现在我们来看下具体是如何扩容的?

假设场景:数组中已经有10个元素,需要添加第11个元素

calculateCapacity方法内部首先会判断elementData数组是否是默认的空数组(看是否往数组里面添加了元素),如果不是默认数组则返回添加元素之后数组所需要的长度

如果添加元素之后的数组长度超出了数组容量,则说明需要扩容,调用grow()方法进行扩容

 grow()方法内部会调用一个交copyOf方法进行扩容,会创建一个1.5倍的新数组,将原来的数组元素挪到新数组中

此时ArrayList扩容为原来的大小+原来大小/2=10+5=15,数组扩容后容量为15

 扩容后的数组示意图如下:

add(E e)添加元素的流程为:

第一步、判断是否需要扩容:

        需要扩容

                ①、计算新数组容量:newCapacity = oldCapacity + (oldCapacity >> 1)

                ②、创建新数组:elementData = Arrays.copyOf(elementData, newCapacity)

第二步、追加元素到数组末尾 。  elementData[size++] =element;

第三步、添加成功

③、ArrayList给指定位置插入元素

示例:

添加指定位置流程如下:

第一步、检查下标是否越界

        越界:抛出IndexOutOfBoundsException异常

第二步、判断是否需要扩容,如果需要扩容则扩容

第三步、后移元素.从指定要插入元素位置依次向后移动一个位置,此时指定要插入的位置为空

第四步、插入新元素。将要插入的元素放入指定位置

第五步、更新数组大小。size+1

        

注意: 其中rangeCheckForAdd(index)方法会检查下标是否越界,如果要插入的元素位置超出了当前数组的容量,会抛出”IndexOutOfBoundsException“的异常

 示意图:

④、删除元素

按照下标位置删除元素

按照内容删除元素


四、总结

通过分析源码我们了解了ArrayList底层增删改查操作具体的细节,再次总结

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/931716.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

cortex-A7 SPI实验 --- STM32MP157

实验目的: 1、数码管显示相同的值 0000 1111 ......9999 2、数码管显示不同的值 1234 一,SPI概念 1,SPI总线是 全双工三线 / 四线同步串行总线,有两根单向数据线(MOSI ,MISO),一根设备片选线&#xff0…

基于SSM的小说网站的设计与实现(论文+源码)_kaic

目 录 1 绪论................................................................................................... 1 1.1 项目背景................................................................................................................ 1 1.2 发展历程..…

《QT+PCL 第五章》点云特征-PFH

QT增加点云特征PFH 代码用法代码 #include <pcl/io/pcd_io.h> #include <pcl/features/normal_3d.h> #include <pcl/features/pfh.h>int main

如何用Python实现转行高薪梦?三个热门方向带你入门

Python是一门非常适合转行的编程语言&#xff0c;它有着丰富的应用场景和学习资源&#xff0c;而且语法简单易懂&#xff0c;学习效率高。如果你想要用Python实现转行梦想&#xff0c;那么你可能会问&#xff0c;Python有哪些热门的工作方向&#xff1f;小编这就为你介绍Python…

VUE笔记(四)vue的组件

一、组件的介绍 1、组件的作用 整个项目都是由组件组成 可以让代码复用&#xff1a;相似结构代码可以做成一个组件&#xff0c;直接进行调用就可以使用&#xff0c;提高代码复用性 可以让代码具有可维护性&#xff08;只要改一处&#xff0c;整个引用的部分全部都变&#xf…

SpringBoot的日志级别你了解吗(自定义打印日志)?

1 SpringBoot日志介绍 ⽇志是程序的重要组成部分&#xff0c;想象⼀下&#xff0c;如果程序报错了&#xff0c;不让你打开控制台看⽇志&#xff0c;那么你能找到报错的原因吗&#xff1f; 如果是简单的错误有可能找出来&#xff0c;但是对于开发中的大多数错误还是需要我们打开…

el-backtop返回顶部的使用

2023.8.26今天我学习了如何使用el-backtop组件进行返回页面顶部的效果&#xff0c;效果如&#xff1a; <el-backtop class"el-backtop"style"right: 20px; bottom: 150px;"><i class"el-icon-caret-top"></i></el-backtop&…

WebGL 绘制函数gl.drawArrays

gl.drawArrays&#xff08;&#xff09;的第1个参数 WebGL方法gl.drawArrays&#xff08;&#xff09;既强大又灵活&#xff0c;通过给第1个参数mode指定不同的值&#xff0c;在这个参数上指定不同的值&#xff0c;我们可以按照不同的规则绘制图形。 下图中的7种基本图形是We…

Java项目-苍穹外卖-Day05-Redis技术应用

1.店铺营业状态设置 需求分析和设计 左上角要求是有回显的 所以至少两个接口 1.查询营业状态接口&#xff08;分为了管理端和用户端&#xff09; 2.修改营业状态接口 因为管理端和用户端路径不同&#xff0c;所以现在是至少三个接口的 可以发现如果存到表里除了id只有一个…

【Day-20慢就是快】代码随想录-栈与队列-删除字符串中的所有相邻重复项

给出由小写字母组成的字符串 S&#xff0c;重复项删除操作会选择两个相邻且相同的字母&#xff0c;并删除它们。 在 S 上反复执行重复项删除操作&#xff0c;直到无法继续删除。 在完成所有重复项删除操作后返回最终的字符串。答案保证唯一。 例&#xff1a; 输入&#xff…

Linux学习(三)----文件打开及创建

1 demo1.c的建立 首先打开终端输入 touch file1 接着输入&#xff1a; vi demo1.c 接着重新打开一个终端&#xff0c;输入&#xff1a; man 2 open 2 demo1.c内容编辑 2.1 复制头文件 2.2 程序基础框架 #include <sys/types.h> #include <sys/stat.h>#include &l…

同态比较算法

参考文献&#xff1a; [PS73] Paterson M S, Stockmeyer L J. On the number of nonscalar multiplications necessary to evaluate polynomials[J]. SIAM Journal on Computing, 1973, 2(1): 60-66.[IZ21] Iliashenko I, Zucca V. Faster homomorphic comparison operations …

基于蛾群算法优化的BP神经网络(预测应用) - 附代码

基于蛾群算法优化的BP神经网络&#xff08;预测应用&#xff09; - 附代码 文章目录 基于蛾群算法优化的BP神经网络&#xff08;预测应用&#xff09; - 附代码1.数据介绍2.蛾群优化BP神经网络2.1 BP神经网络参数设置2.2 蛾群算法应用 4.测试结果&#xff1a;5.Matlab代码 摘要…

cpolar做一个内网穿透

因为不在公司&#xff0c;需要访问公司的数据库&#xff0c;所以做一个内网穿透 下载安装 下载地址&#xff1a; https://dashboard.cpolar.com/get-started 下载后是个压缩包&#xff0c;解压后傻瓜式安装 操作隧道 安装后打开Cpolar Web UI 登录账号&#xff0c;查看隧…

python面试题--1

目录 python面试题 1&#xff09;什么是Python&#xff1f;使用Python有什么好处&#xff1f; 2&#xff09;什么是PEP 8&#xff1f; 3&#xff09;什么是序列化和非序列化&#xff1f; 4&#xff09;如何解释Python&#xff1f; 5&#xff09;如何在Python中内存管理&a…

Unity3D软件安装包分享

目录 一、软件简介 二、软件下载 一、软件简介 Unity3D是一款全球知名的游戏开发引擎&#xff0c;由Unity Technologies公司开发。它提供了一个跨平台、多功能的开发环境&#xff0c;支持创建2D和3D游戏、交互式应用、虚拟现实、增强现实等多种类型的应用程序。以下是Unity3D…

山西电力市场日前价格预测【2023-08-27】

日前价格预测 预测明日&#xff08;2023-08-27&#xff09;山西电力市场全天平均日前电价为318.11元/MWh。其中&#xff0c;最高日前电价为356.66元/MWh&#xff0c;预计出现在19: 15。最低日前电价为273.48元/MWh&#xff0c;预计出现在04: 30。 价差方向预测 1&#xff1a; 实…

01-Flask-简介及环境准备

Flask-简介及环境准备 前言简介特点Flask 与 Django 的比较环境准备 前言 本篇来介绍下Python的web框架–Flask。 简介 Flask 是一个轻量级的 Web 框架&#xff0c;使用 Python 语言编写&#xff0c;较其他同类型框架更为灵活、轻便且容易上手&#xff0c;小型团队在短时间内…

785. 判断二分图

785. 判断二分图 原题链接&#xff1a;完成情况&#xff1a;解题思路&#xff1a;参考代码&#xff1a; 原题链接&#xff1a; 785. 判断二分图 https://leetcode.cn/problems/is-graph-bipartite/description/ 完成情况&#xff1a; 解题思路&#xff1a; 题目解释&#x…

清洁能源使用的社会发展意义

应用清洁能源是转变经济增加途径的有效手段&#xff0c;能够在减少污染物、降低企业经营成本的同时&#xff0c;提高企业经济效益和社会经济效益。 应用清洁能源是保护环境的最佳方式和必然选择&#xff0c;改变末端治理的现状&#xff0c;采取以预防为主的环境保护与发展理…