线性结构-稀疏数组

线性结构-稀疏数组

数据结构包括:线性结构非线性结构

线性结构

  1. 线性结构作为最常用的数据结构,其特点是数据元素之间存在一对一的线性关系
  2. 线性结构有两种不同的存储结构,即顺序存储结构和链式存储结构。顺序存储的线性表称为顺序表,顺序表中的存储元素是连续的
  3. 链式存储的线性表称为链表,链表中的存储元素不一定是连续的,元素节点中存放数据元素以及相邻元素的地址信息
  4. 线性结构见的有:组队列、链表和栈

非线性结构

非线性结构包括:二维数组,多维数组,广义表,树结构,图结构

今天我们的主角是线性结构中的稀疏数组,今天讲解一下什么是稀疏数组,稀疏数组什么时候该用,以及怎么用。

什么是稀疏数组

当一个数组中大部分元素为0,或者为同一个值的数组时,可以使用稀疏数组来保存该数组。用于减少存放这些数据使用的空间。

稀疏数组的处理方法是:

1)记录数组一共有几行几列,有多少个不同的值

2)把具有不同值的元素的行列及值记录在一个小规模的数组中,从而缩小程序的规模

用图说话:

原数组:(有很多0,这个时候可以选择稀疏数组进行压缩空间)

image.png

稀疏数组:(第一行分别代表有6行,7列,以及有8个值,最终构成一个3列(8+1)行的二维数组)

image.png

稀疏数组怎么用

image.png

代码实现:原数组是一个11*11的二维数组

生成稀疏数组

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
/**
* 生成稀疏数组
* @param cheeseArr
* @param sum
*/
private static int[][] generateSparseArray(int[][] cheeseArr, int sum) {
//2.创建对应的稀疏数组 一个3列 (非0项数字出现次数和+1)行 (多了一个统计原始数组行列和所有非0项出现次数和的行) 数组
int sparseArr[][] = new int[sum +1][3];
//给数组赋值
sparseArr[0][0] = 11; //行
sparseArr[0][1] = 11; //列
sparseArr[0][2] = sum; //有效值个数

//便利二维数组,将非0值遍历到稀疏数组
//定义一个计数器,记录是第几个数
int count = 0;
for (int i = 0; i < cheeseArr.length; i++) {
for (int j = 0; j < cheeseArr[i].length; j++) {
if(cheeseArr[i][j]!=0) {
count++;
sparseArr[count][0] = i; //行
sparseArr[count][1] = j; //列
sparseArr[count][2] = cheeseArr[i][j]; //值
}
}
}

//输出稀疏数组
System.out.println();
System.out.println("得到的稀疏数组为:");
for (int i = 0; i < sparseArr.length; i++) {
System.out.printf("%d\t %d\t %d\t",sparseArr[i][0],sparseArr[i][1],sparseArr[i][2]);
System.out.println();
}
return sparseArr;
}

解析稀疏数组

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
/**
* 通过稀疏数组还原原数组
* 思路:先读取第一行数据,创建原始的二维数组
* 读取稀疏数组后几行数据并赋值给原始的二维数组即可
* @param sparseArr
* @return
*/
public static int[][] getOriginArr(int[][] sparseArr){
int[][] originArray = new int[sparseArr[0][0]][sparseArr[0][1]];
for (int i = 1; i < sparseArr.length; i++) {
originArray[sparseArr[i][0]][sparseArr[i][1]] = sparseArr[i][2];
}
System.out.println("原始数组为:");
for (int i = 0; i < originArray.length; i++) {
for (int j = 0; j < originArray[i].length; j++) {
System.out.printf("%d\t",originArray[i][j]);
}
System.out.println();
}
return originArray;
}

总的代码为:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
package top.ryan.sparsearray;

/**
* 稀疏数组
*/
public class SparseArray {
public static void main(String[] args) {
//创建一个原始的二维数组11*11
//0-》没有棋子 1-》黑子 2-》蓝子
int cheeseArr[][] = new int[11][11];
cheeseArr[1][2] = 1;
cheeseArr[2][3] = 2;
cheeseArr[3][3] = 1;
cheeseArr[4][5] = 2;
//输出原始数组
for (int[] arr : cheeseArr) {
for (int num : arr) {
System.out.printf("%d\t",num);
}
System.out.println();
}

//将二维数组转为稀疏数组
//1.先便利二维数组,得到非0数组的个数
int sum = 0;
for (int i = 0; i < cheeseArr.length; i++) {
for (int j = 0; j < cheeseArr[i].length; j++) {
if(cheeseArr[i][j]!=0){
sum++;
}
}
}

int[][] sparseArr = generateSparseArray(cheeseArr, sum);
//从稀疏数组还原原始数组
int[][] originArr = getOriginArr(sparseArr);
}

/**
* 生成稀疏数组
* @param cheeseArr
* @param sum
*/
private static int[][] generateSparseArray(int[][] cheeseArr, int sum) {
//2.创建对应的稀疏数组 一个3列 (非0项数字出现次数和+1)行 (多了一个统计原始数组行列和所有非0项出现次数和的行) 数组
int sparseArr[][] = new int[sum +1][3];
//给数组赋值
sparseArr[0][0] = 11; //行
sparseArr[0][1] = 11; //列
sparseArr[0][2] = sum; //有效值个数

//便利二维数组,将非0值遍历到稀疏数组
//定义一个计数器,记录是第几个数
int count = 0;
for (int i = 0; i < cheeseArr.length; i++) {
for (int j = 0; j < cheeseArr[i].length; j++) {
if(cheeseArr[i][j]!=0) {
count++;
sparseArr[count][0] = i; //行
sparseArr[count][1] = j; //列
sparseArr[count][2] = cheeseArr[i][j]; //值
}
}
}

//输出稀疏数组
System.out.println();
System.out.println("得到的稀疏数组为:");
for (int i = 0; i < sparseArr.length; i++) {
System.out.printf("%d\t %d\t %d\t",sparseArr[i][0],sparseArr[i][1],sparseArr[i][2]);
System.out.println();
}
return sparseArr;
}

/**
* 通过稀疏数组还原原数组
* 思路:先读取第一行数据,创建原始的二维数组
* 读取稀疏数组后几行数据并赋值给原始的二维数组即可
* @param sparseArr
* @return
*/
public static int[][] getOriginArr(int[][] sparseArr){
int[][] originArray = new int[sparseArr[0][0]][sparseArr[0][1]];
for (int i = 1; i < sparseArr.length; i++) {
originArray[sparseArr[i][0]][sparseArr[i][1]] = sparseArr[i][2];
}
System.out.println("原始数组为:");
for (int i = 0; i < originArray.length; i++) {
for (int j = 0; j < originArray[i].length; j++) {
System.out.printf("%d\t",originArray[i][j]);
}
System.out.println();
}
return originArray;
}
}

输出结果为:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
0	0	0	0	0	0	0	0	0	0	0	
0 0 1 0 0 0 0 0 0 0 0
0 0 0 2 0 0 0 0 0 0 0
0 0 0 1 0 0 0 0 0 0 0
0 0 0 0 0 2 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0

得到的稀疏数组为:
11 11 4
1 2 1
2 3 2
3 3 1
4 5 2
原始数组为:
0 0 0 0 0 0 0 0 0 0 0
0 0 1 0 0 0 0 0 0 0 0
0 0 0 2 0 0 0 0 0 0 0
0 0 0 1 0 0 0 0 0 0 0
0 0 0 0 0 2 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0
-------------本文结束感谢您的阅读-------------