今日开始总结数据结构相关的知识,本章复习了数据结构的基本知识点、稀疏数组和队列相关的知识。
数据结构
一、数据结构与算法的关系
1、数据结构是一门研究组织数据方式的学科,有了编程语言也就有了数据结构;
2、程序 = 数据结构 + 算法;
3、数据结构是算法的基础。
二、线性结构与非线性结构
1、数据结构的结构
数据结构的存储结构分为线性结构和非线性结构。
2、线性结构
(1)线性结构作为最常用的数据结构,其特点是数据元素之间存在一对一的线性关系;
(2)线性结构有两种不同的存储结构,即顺序存储结构和链式存储结构。顺序存储的线性表称为顺序表,顺序表中的存储元素是连续的;
(3)链式存储的线性表称为链表,链表中的存储元素不一定是连续的,元素结点中存放数据元素以及相邻元素的地址信息;
(4)线性结构常见的有:数组、队列、链表和栈。
3、非线性结构
(1)包括:二维数组、多维数组、广义表、树结构、图结构。
稀疏数组
一、基本介绍
当一个数组中大部分元素为0(初始值),或者为同一个值的数组时,可以使用稀疏数组来保存该数组。
1、处理方法:
(1)记录一个数组一共有几行几列,有多少个不同的值;
(2)把具有不同的元素的行列及值记录在一个小规模的数组中,从而缩小程序的规模。
稀疏数组的第1行([0]号位置)记录的是原始数组的行数(6行)和列数(7列)和非零元素的个数(5个)
稀疏数组的第二行开始([1]及以后的行),行列存放的是非零元素在原始数组中的行的位置,列列存放的是同一个非零元素的列的位置,值的位置存放的是非零元素的实际值。
二、实现思路
(1)二维数组转稀疏数组
- 遍历原始的二维数组,得到有效数据的个数sum;
- 根据sum就可以创建稀疏数组sparseArr int【sum + 1】【3】;
- 将二维数组的有效数据存入稀疏数组。
(2)稀疏数组转原始数组
- 先读取稀疏数组的第一行,根据第一行的数据创建二维数组;
- 再读取稀疏数组的后几行数据,并赋值给原始的数组即可。
三、代码实现
- 创建一个原始二维数组并赋值
| 1 | //二维数组转稀疏数组 | 
(1) 二维数组转稀疏数组实现
- 遍历原始二维数组,获取有效的数据个数 - 1 
 2
 3
 4
 5
 6
 7
 8
 9
 10
 11
 12- // 稀疏数组 
 // 获取非初始化数据的个数
 int r = arr.length;//二维数组的行
 int l = arr[0].length;//二维数组的列
 int sum = 0;//非0元素的个数
 for (int[] row : arr) {
 for (int data : row) {
 if (data != 0) {
 sum++;
 }
 }
 }
 
- 根据二维数组的非零元素的个数sum创建稀疏数组 - 1 
 2
 3
 4
 5
 6- // 创建稀疏数组 
 int sparseArr[][] = new int[sum + 1][3];
 // 对稀疏数组的第一行进行赋值,二维数组的信息
 sparseArr[0][0] = arr.length;
 sparseArr[0][1] = arr[0].length;
 sparseArr[0][2] = sum;
- 将二维数组的有效个数存入稀疏数组 - 1 
 2
 3
 4
 5
 6
 7
 8
 9
 10
 11
 12- // 获取非0数据并赋值 
 int count = 0;
 for (int i = 0; i < arr.length; i++) {
 for (int j = 0; j < arr[0].length; j++) {
 if (arr[i][j] != 0) {
 count++;
 sparseArr[count][0] = i;
 sparseArr[count][1] = j;
 sparseArr[count][2] = arr[i][j];
 }
 }
 }
- 遍历稀疏数组查看结果 
(2)稀疏数组转二维数组实现
- 先读取稀疏数组的第一行,根据第一行的数据,创建原始二位数组 - 1 
 2
 3- //稀疏数组转二维数组 
 //创建一个二维数组
 int arr1[][] = new int[sparseArr[0][0]][sparseArr[0][1]];
 
- 在读取稀疏数组的后几行数据,并赋值给二维数组 - 1 
 2
 3
 4
 5
 6
 7
 8- // 将稀疏数组中的值赋值给二维数组 
 for (int i = 1; i < sparseArr.length; i++) {
 int rows = sparseArr[i][0];
 int c = sparseArr[i][1];
 int data = sparseArr[i][2];
 arr1[rows][c] = data;
 }
 
- 运行结果 
队列
一、基本介绍
1、队列是一个有序列表,可以使用链表和数组实现;
2、遵循先进先出的原则。即:先存入队列的数据先取出,后存入的数据后取出。
/数组队列逻辑结构图 (一).JPG)
二、数组队列思路
1、队列本身是一个有序列表,若使用数组存储数据则需声明maxSize(数组的最大容量);
2、因数组需要输出,所以需要两个变量分别指向队列的头元素和尾元素;
3、front为指向队列的头元素索引。默认值为-1;
4、rear为指向队列的尾元素索引。默认值为-1;
5、当需要向队列中添加数据时需判断队列是否已满,若满则将rear的值加一然后存入元素;
6、队列为空的判断方法:rear == front;
7、队列是否已满的判断方法为 rear == maxSize - 1或 rear + 1 == maxSize;
8、当取元素时将front加一,然后将 queue[front] 的值返回。
三、代码实现
1、创建一个队列类
| 1 | class ArraysQueue { | 
2、判断队列是否为空与是否已满
| 1 | //判断队列是否为空——isEmpty | 
3、向队列中添加元素
判断非空后,先将指向队列尾部的索引后移一位指向一个空的位置,然后将数据存入数组。
| 1 | //添加元素——addQueue | 
4、取队头元素
待判断结束之后,将队头索引先向后移动一位,只想队头元素,然后取出元素,此时取出的数据不需要再将其删除,因为下次会直接跳过该元素。
| 1 | //取队头元素getQueue | 
5、输出队列
使用for循环输出队列,使 i 的值等于(front + 1),使队列从头元素开始遍历,当 i 的值等于队尾的索引值时停止循环。
| 1 | //输出队列show | 
6、输出获取头元素
| 1 | //输出获取头元素——headQueue | 
环形数组队列
一、基本介绍
1、环形数组队列修复了数组队列不能一致存放数据的缺点,但还是和数组队列一样需要设置maxSize;
2、环形数组只是再逻辑上时环形的,但其实在物理存储结构上依然是和数组队列一样的。
二、环形数组队列实现思路
1、front指向数组(队列)的第一个元素queue[0] ,front的初始值设为0;
2、rear指向数组(队列)的最后一个元素的后一个位置,因为空出来一个空间用来做约定,rear的初始值为0;
3、当队列满的判断条件为(rear + 1)% maxSize == front时;
4、当队列为空的判断条件为 rear == front;
5、队列中有效数据的个数为( rear + maxSize - front)% maxSize。
三、环形数组队列的代码实现
1、创建一个环形队列类
| 1 | public class CircleArraryQueueDemo { | 
2、判断队列是否为空与已满
| 1 | //判断队列是否为空——isEmpty | 
3、向队列添加元素
| 1 | //添加元素——addQueue | 
4、获取队列中有效元素的个数
| 1 | //获取队列中有效元素的个数 | 
5、输出队列
| 1 | //输出队列show | 
6、获取头元素
| 1 | //取队头元素getQueue | 
7、输出头元素
| 1 | //输出获取头元素——headQueue | 
参考资料:
 
          
          
          
         
     
          
         
          
        