忽然心血来潮,看了一下简单的数据结构,入门级别的,不要介意!
定义
稀疏数组又可以叫做稀疏矩阵。 稀疏数组是一个二维数组中有效信息较少,或者说非0元素远少于值为0的元素的数组。这里的0元素可以自己定义,找一个元素比较集中的就可以。
通常认为一个矩阵中非零元素的总数比上矩阵所有元素总数的值小于等于5%时, 则称该矩阵为稀疏矩阵,该比值称为这个矩阵的稠密度。
存在的意义
当一个大型二维数组中的0元素远多于非0元素时,储存或读取该数组是比较耗费机能的,因为系统要储存每一个该二维数组中的元素,即使有许多元素都为0,没有意义。那么,能不能将该矩阵进行简化,只保留少量的非0元素组成新的数组(或矩阵),这样一来只除存或是读取该简化数组,就能节约机能,提高运算效率。所以,稀疏数组出现了。
案例
棋盘的保存到磁盘和复盘
理解
将棋盘中无子的地方定义成0,黑子定义成1,蓝子定义成2 。直接记录位置的值,没有意义的数据太多,浪费空间资源。 这个时候我们就可以使用稀疏数组来对该二维数组进行一个压缩
当一个数组中大部分元素是0,或者为同一个值的数组时,可以使用稀疏数组来保存该数组。
稀疏数组的处理方法是:
1) 记录数组一共有几行几列,有多少个不同的值 (总体的基本信息记录一下)
2) 把具有不同值的元素的行列及值记录在一个小规模的数组中,从而缩小程序的规模
稀疏数组的组成样例
行row | 列col | 值value |
---|---|---|
原数组的行数 | 原数组的列数 | 值得总个数 |
3这个值在原数组的行 | 3这个值在原数组的列 | 3 |
。。。 | 。。。 | 。。。 |
图例
稀疏数组的列是固定的,3列,行数不固定,根据值的个数来决定
代码
代码实现下面棋盘的保存和复原
保存棋盘为稀疏数组,并保存到磁盘
import java.io.*;
/*
存盘
*/
public class Save {
public static void main(String[] args) throws IOException {
//棋盘现状
int[][] arr = new int[11][11] ;
arr[1][2] = 1;
arr[2][3] = 2;
int sum = 0;
for (int i=0;i<11;i++){
for (int j=0;j<11;j++){
System.out.print(arr[i][j] + " ");
if (arr[i][j] != 0){
sum+=1;
}
}
System.out.println();
}
System.out.println("非0元素一共有"+sum+"个");
//创建稀疏数组
int[][] sparseArr = new int[sum+1][3];
sparseArr[0][0] = 11;
sparseArr[0][1] = 11;
sparseArr[0][2] = sum;
int count = 0; //记录第几个非0值
for (int i=0;i<11;i++){
for (int j=0;j<11;j++){
if(arr[i][j] != 0){
count+=1;
sparseArr[count][0] = i;
sparseArr[count][1] = j;
sparseArr[count][2] = arr[i][j];
}
}
}
//查看稀疏数组
for (int i=0;i<sum+1;i++){
for (int j=0;j<3;j++){
System.out.print(sparseArr[i][j] + "\t");
}
System.out.println();
}
//存盘
File file = new File("D:\\1.txt");
BufferedWriter bw = new BufferedWriter(new FileWriter(file));
for (int i=0;i<sum+1;i++){
for (int j=0;j<3;j++){
bw.write(sparseArr[i][j]+"\t");
}
bw.flush();
bw.newLine();
}
System.out.println("导入数据文件完成");
bw.close();
}
}
读取存储的文件,复原棋盘
import java.io.*;
import java.util.Collections;
/*
复盘
*/
public class Analyse {
public static void main(String[] args) throws IOException {
BufferedReader bw = new BufferedReader(new FileReader(new File("D:\\1.txt")));
String data = null;
int row = 0; //行
int col = 0; //列
//读取第一行
if((data=bw.readLine())!=null){
String[] split = data.split("\t");
row = Integer.parseInt(split[0]);
col = Integer.parseInt(split[1]);
}else{
System.out.println("没有数据,结束执行");
System.exit(0);
}
//创建原数组
int[][] arr = new int[row][col];
//读取除了第一行的数据
int count = 0;
while((data=bw.readLine())!=null){
String[] split = data.split("\t");
arr[Integer.parseInt(split[0])][Integer.parseInt(split[1])] = Integer.parseInt(split[2]);
}
for (int i=0;i<row;i++){
for (int j=0;j<col;j++){
System.out.print(arr[i][j] + " ");
}
System.out.println();
}
}
}