Java算法与数据结构入门——稀疏数组
第一次写博客,如有表达含糊等问题,请见谅…
算法是什么
算法(Algorithm)是指解题方案的准确而完整的描述,是一系列解决问题的清晰指令,算法代表着用系统的方法描述解决问题的策略机制。也就是说,能够对一定规范的输入,在有限时间内获得所要求的输出。如果一个算法有缺陷,或不适合于某个问题,执行这个算法将不会解决这个问题。不同的算法可能用不同的时间、空间或效率来完成同样的任务。一个算法的优劣可以用“空间复杂度”与”时间复杂度“来衡量。
数据结构是什么
数据结构是计算机存储、组织数据的方式。数据结构是指相互之间存在一种或多种特定关系的数据元素的集合。通常情况下,精心选择的数据结构可以带来更高的运行或者存储效率。数据结构往往同高效的检索算法和索引技术有关。
前提
在阅读本文前,请保证你已掌握基础的c语言或者java语言的基础,我尽量以最简单的方式讲清楚这次的内容,那么,废话不多说,我们直接进入正题!
二维数组
二维数组上本质上是以数组作为数组元素的数组,它给我的感觉有点像x,y的坐标表,本质上用于存储数据,为非线性结构,在数据大多为有效值(即不为0)的时候有存在的必要性,那么当我们创建一个超大的二维数组,而其中的有效值(不为0的值)却占比很少的时候,且数据与数据间无明显的排序关系,就可以说我们的二维数组保存了很多的“无用的数据”,这时候就要引出我们的“稀疏数组”的概念。
稀疏数组
稀疏数组,故名思意,就是“稀疏”的数组嘛,它的主要用途用于在矩阵中(即二维数组中),可以利用所谓的“压缩算法”,将前面提到的二维数组压缩为一个稀疏数组,节约存储空间。
下面,我来讲解下第二个数组的形式,我就简称它为第二数组吧,第二数组第一行,用于记录原数组的行数,列数,与总共有多少个有效值。而后面的第二行及以后,则用于单个数据的坐标定位和有效值。下面展示代码:
//首先我们先创建一个数组并给部分的点进行赋值
int[][] OriginArray = new int[11][11];
OriginArray[1][2] = 1;
OriginArray[2][3] = 2;
//遍历数组并打印
for (int[] ints : OriginArray) {
for (int anInt : ints) {
System.out.printf("%d\t",anInt);
}
System.out.println();
}
结果为:
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 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 0 0 0
0 0 0 0 0 0 0 0 0 0 0
得到了我们理想中的二维数组,然后我们可以通过遍历数组,得到我们该数组保存有多少有效值
//遍历数组得到该二维数组总共有多少个有效值
int sum = 0;
for (int i = 0; i < 11; i++) {
for (int j = 0; j < 11; j++) {
if(OriginArray[i][j]!=0){
sum++;
}
}
}
然后开始创建一个稀疏数组,并将有效值保存在稀疏数组中
//创建稀疏数组 格式为newArray[sum+1][3]
int[][] spraseArray = new int[sum+1][3];
spraseArray[0][0] = 11;
spraseArray[0][1] = 11;
spraseArray[0][2] = sum;
//遍历二维数组,讲非0的值存入到稀疏数组中,进行压缩处理
int row = 1;
for (int i = 0; i < 11; i++) {
for (int j = 0; j < 11; j++) {
if(OriginArray[i][j]!=0){
spraseArray[row][0] = i;
spraseArray[row][1] = j;
spraseArray[row][2] = OriginArray[i][j];
row++;
}
}
}
结果为:
11 11 2
1 2 1
2 3 2
然后我们就完成了所谓的压缩处理,经过io处理之后可以写入本地文件中,减少了存储空间。
最后还要将稀疏数组转为二维数组到实际开发中去应用
所以我们还要会识别稀疏数组
//稀疏数组转二维数组
int new_row = spraseArray[0][0];
int new_col = spraseArray[0][1];
int[][] newArray = new int[new_row][new_col];
new_col = 0;
new_col = 0;
int value= 0 ;
//创建数组
for (int i = 1; i <row ; i++) {
new_row = spraseArray[i][0];
new_col = spraseArray[i][1];
value = spraseArray[i][2];
newArray[new_row][new_col] = value;
}
打印结果为:
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 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 0 0 0
0 0 0 0 0 0 0 0 0 0 0
即大功告成,最后还可以将方法封装起来,这样的话,使用起来就可以更方便且可以解耦。
最后附上我的源码:
public class SparseArray {
public static void main(String[] args) {
int[][] OriginArray = new int[11][11];
OriginArray[1][2] = 1;
OriginArray[2][3] = 2;
//遍历数组并打印
for (int[] ints : OriginArray) {
for (int anInt : ints) {
System.out.printf("%d\t",anInt);
}
System.out.println();
}
//遍历数组得到该二维数组总共有多少个有效值
int sum = 0;
for (int i = 0; i < 11; i++) {
for (int j = 0; j < 11; j++) {
if(OriginArray[i][j]!=0){
sum++;
}
}
}
//创建稀疏数组 格式为newArray[sum+1][3]
int[][] spraseArray = new int[sum+1][3];
spraseArray[0][0] = 11;
spraseArray[0][1] = 11;
spraseArray[0][2] = sum;
//遍历二维数组,讲非0的值存入到稀疏数组中,进行压缩处理
int row = 1;
for (int i = 0; i < 11; i++) {
for (int j = 0; j < 11; j++) {
if(OriginArray[i][j]!=0){
spraseArray[row][0] = i;
spraseArray[row][1] = j;
spraseArray[row][2] = OriginArray[i][j];
row++;
}
}
}
//System.out.println("row="+row);
System.out.println("=============================");
for (int[] ints : spraseArray) {
for (int anInt : ints) {
System.out.printf("%d\t",anInt);
}
System.out.println();
}
//稀疏数组转二维数组
int new_row = spraseArray[0][0]; //11
int new_col = spraseArray[0][1]; //11
int[][] newArray = new int[new_row][new_col];
new_col = 0;
new_col = 0;
int value= 0 ;
//创建数组
for (int i = 1; i <row ; i++) {
new_row = spraseArray[i][0];
new_col = spraseArray[i][1];
value = spraseArray[i][2];
newArray[new_row][new_col] = value;
}
System.out.println("===================================");
for (int[] ints : newArray) {
for (int anInt : ints) {
System.out.printf("%d\t",anInt);
}
System.out.println();
}
}
}
``