浅谈Java数据结构之稀疏数组知识总结

稀疏数组

  • 当一个数组中的元素大多为0或者相同元素的时候,可以用稀疏数组来压缩
  • 稀疏数组只记录 行row 列col 值value

将下列的二维数组转为稀疏数组,如下两图所示


1.实现二维数组转为稀疏数组的步骤:

  • 遍历数组,得到数组中 不为0的个数,并记录为sum,作为稀疏数组第0行的 value
  • 遍历数组,将数组中不为0的数的行和列和值分别写入稀疏数组的 row col val 中

代码实现:

public class SparseArray {
    public static void main(String[] args) {

        // 创建一个原始二维数组
        // 0表示没有棋子,1,2各表示一种棋
        int chessArr[][] = new int[8][8];
        chessArr[1][1] = 1;
        chessArr[2][2] = 2;

        // 遍历原始数组,获得不等于 0 的个数,并输出原始数组
        int sum = 0;
        System.out.println("原始数组:");
        for (int[] ints : chessArr) {
            for (int anInt : ints) {
                System.out.print(anInt+"\t");
                if (anInt != 0){
                    sum++;
                }
            }
            System.out.println();
        }
        System.out.println(sum);

        // 创建稀疏数组并赋值
        int sparseArray[][] = new int[sum+1][3];
        int row = chessArr.length; // 原数组的行数
        int col = chessArr[0].length; // 原数组的列数
        sparseArray[0][0] = row;
        sparseArray[0][1] = col;
        sparseArray[0][2] = sum;

        // 遍历原始数组并赋值给稀疏数组
        int count = 0; // count 为计数器
        for (int i = 0;i < row;i++) {
            for (int j = 0;j < col;j++) {
                if (chessArr[i][j] != 0) {
                    count++;
                    sparseArray[count][0] = i;
                    sparseArray[count][1] = j;
                    sparseArray[count][2] = chessArr[i][j];
                }
            }
        }

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

    }
}

2.实现二维数组转稀疏数组的步骤

  • 根据稀疏数组的第一行创建新的二维数组
  • 遍历稀疏数组,将row col val 赋给新的二维数组

代码实现:

public class SparseArray {
    public static void main(String[] args) {

		...... // 接上一段代码

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

        // 创建新的二维数组
        int newChessArray[][] = new int[sparseArray[0][0]][sparseArray[0][1]];
        for (int i = 1 ;i < sparseArray.length;i++) {
            newChessArray[sparseArray[i][0]][sparseArray[i][1]] = sparseArray[i][2];
        }

        // 输出新的二维数组
        System.out.println("恢复后的二维数组是:");
        for (int[] ints : newChessArray) {
            for (int anInt : ints) {
                System.out.print(anInt+"\t");
            }
            System.out.println();
        }
    }
}

3.将稀疏数组写入磁盘

public static void main(String[] args) {
    ........
	// 将稀疏数组存入磁盘
    FileOutputStream fw = null;
    try {
        fw = new FileOutputStream("sparseArray.txt");
        // 遍历写入磁盘
        for (int i = 0; i < sparseArray.length; i++) {
            for (int j = 0; j < 3; j++) {
                fw.write(sparseArray[i][j]);
            }
        }
        fw.flush();
    } catch (FileNotFoundException e) {
        e.printStackTrace();
    } catch (IOException e) {
        e.printStackTrace();
    } finally {
        if (fw != null){
            fw.close();
        }
    }
}

4.从磁盘读取稀疏数组

public static void main(String[] args) {
    .......
    // 从磁盘读取稀疏数组
    FileInputStream fi = null;
    int newSparseArray[][] = new int[sum+1][3];  // sum 指前面二维数组有值的个数
    try {
        fi = new FileInputStream("sparseArray.txt");
        for (int i = 0;i < newSparseArray.length;i++) {
            for (int j = 0;j < 3;j++){
                newSparseArray[i][j] = fi.read();
            }
        }
    } catch (FileNotFoundException e){
        e.printStackTrace();
    } finally {
        if (fi != null){
            fi.close();
        }
    }
}

到此这篇关于浅谈Java数据结构之稀疏数组知识总结的文章就介绍到这了,更多相关Java稀疏数组内容请搜索我们以前的文章或继续浏览下面的相关文章希望大家以后多多支持我们!

(0)

相关推荐

  • Java使用5个线程计算数组之和

    前言 之前写过多线程累加计数,原理跟本篇类似,传送门 累加计数比计算数组之和逻辑稍微简单一点,如果对于这块不熟悉的,可以先看下累加计数. 基本思想已经在之前那篇文章里写过了,这里就直接贴代码了. 这里分别通过自己创建线程来实现功能,还有通过线程池来实现功能.思想都差不多.只是代码写法略有不同.仅供参考. 代码一: 五个线程交替累加计算数组之和,这种方法其实不如单线程直接累加快,因为交替累加需要前一个线程计算的结果. package test; import java.util.concurren

  • Java基础语法之二维数组详解

    一.二维数组 进入正题之前.首先为了便于大家理解,我画了一个图: xx枪战游戏中, 我是一个刚刚注册账号的小白,系统送了我两把枪,此时,我的武器库只有这么一层(可以理解为一位数组,枪就是对应的数组中对应的元素) 经过艰苦卓绝的战斗,终于有了一笔钱,现在我打算配置好的游戏装备,我现在有了一个枪柜,它可以存放三层的枪械,每一层都可以放多把武器(这个就是二维数组,有多层,每层都是一个一维数组) 随着游戏时长和我的高超技术,获取游戏装备的效率越来越高了,一个枪柜已经存不下了,于是,我就有了多个枪柜(这个

  • Java 数组的两种初始化方式

    一.数组 1.数组中存储元素的类型是统一的,每一个元素在内存中所占用的空间大小是相同的,知道数组的首元素的内存地址,要查找的元素只要知道下标,就可以快速的计算出偏移量,通过首元素内存地址加上偏移量,就可以快速计算出要查找元素的内存地址.通过内存地址快速定位该元素,所以数组查找元素的效率较高. 2.随机的对数组进行增删元素,当增加元素的时候,为了保证数组中元素在空间存储上是有序的,所以被添加元素位置后面的所有元素都要向后移动,删除元素也是,后面所有的元素要向前移动,所以数组的增删元素​效率很低.

  • Java基础之数组详解

    前言 我们了解数组这个概念之前,我们先思考下面几个问题. 如果我们需要两个数据,那么直接创建两个变量即可 int a; int b; 如果需要五个数据,那么可以创建五个变量 int a; int b; int c; int d; int f; 但如果我们需要100个甚至是1万个数据,那么我们创一万个变量?显然这是不现实的.这个时候就需要我们的数组来起作用!帮我们"批量"创建变量. 由上可以得出:数组的本质就是让我们能"批量"创建相同类型的变量! 一.数组的概念 数组

  • 教你怎么用Java数组和链表实现栈

    一.何为栈? 栈(stack)又名堆栈,它是一种运算受限的线性表.限定仅在表尾进行插入和删除操作的线性表.这一端被称为栈顶,相对地,把另一端称为栈底.向一个栈插入新元素又称作进栈.入栈或压栈,它是把新元素放到栈顶元素的上面,使之成为新的栈顶元素:从一个栈删除元素又称作出栈或退栈,它是把栈顶元素删除掉,使其相邻的元素成为新的栈顶元素. 栈可以类比成现实生活中的弹夹或者羽毛球桶 二.用数组实现栈 用数组模拟栈的思路分析如图: 1.定义一个top变量(指针)表示栈顶初始化为-1. 2.定义一个变量来记

  • java使用IO流对数组排序实例讲解

    在学会了java中io流的使用后,我们对于数组的排序,又多了一种使用方法.大家知道流处理数据的效率是比较理想的,那么在具体操作数组排序上,很多人对于排序的方法还没有明确.下面我们先java使用流对数组排序的思路为大家进行梳理,然后带来对应的实例代码方法. 1.排序思路 (1)从字符输入流中读取文本,缓冲各个字符,从而实现字符.数组和行的高效读取 (2)询问用户需要多少位数的数组 (3)转换为数字类型 (4)将用户输入数字存入数组 (5)把数组按排序需求并打印出来 2.实例 public stat

  • Java 自定义动态数组方式

    Java自定义动态数组 1.静态数组向动态数组转变 (1)静态数组,数组空间固定长度 这个数组空间总长为4,如果此时新插入一个数据就会报数组空间不足 (2)静态数组如何转变成动态数组 第一步:创建一个空间是data数组两倍的newData数组(扩容): 第二步:把data数组中的元素全部赋值到newData数组: 2.数组扩容程序 // 数组扩容 private void resize(int newCapacity){ E[] newData = (E[]) new Object[newCap

  • java数组算法例题代码详解(冒泡排序,选择排序,找最大值、最小值,添加、删除元素等)

    数组算法例题 1.数组逆序 第一个和最后一个互换,第二个和倒数第二个互换,就相当于把数组想下图一样,进行对折互换,如果数组个数为奇数,则中间保持不变其余元素互换即可 import java.util.Arrays; class Demo12 { public static void main (String[] args) { int[] arr = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9}; System.out.println(Arrays.toString(arr));

  • 解决java main函数中的args数组传值问题

    这几天面试中有遇到关于main数组中的args数组传值的问题,一般是从命令提示符中传值,也可以直接在java代码中赋值. 而且这个数组的长度是动态的,根据传值的个数确定数组的长度. 1.从命令提示符中传值 我在桌面新建了一个文本文档重命名为TestMain.java,代码如下 public class TestMain { public static void main(String[] args) { System.out.println("hello "+args[0]); Sys

  • 浅谈Java数据结构之稀疏数组知识总结

    稀疏数组 当一个数组中的元素大多为0或者相同元素的时候,可以用稀疏数组来压缩 稀疏数组只记录 行row 列col 值value 将下列的二维数组转为稀疏数组,如下两图所示 1.实现二维数组转为稀疏数组的步骤: 遍历数组,得到数组中 不为0的个数,并记录为sum,作为稀疏数组第0行的 value 遍历数组,将数组中不为0的数的行和列和值分别写入稀疏数组的 row col val 中 代码实现: public class SparseArray { public static void main(S

  • 浅谈java中的一维数组、二维数组、三维数组、多维数组

    这个数组可以看做新手学习,从一维数组 到 多维 数组 循环渐进,其实看起也很简单,一看便知,众所周知,一维.二维或许经常用到,用到二维以上应该就很少了. public class test { public static void main(String[] args) { /*一维数组*/ int num[] = {0,1,2}; /*下面输出 3 行数据,0 ~ 2*/ for (int i = 0; i < num.length; i++) { System.out.println("

  • 浅谈Java设计模式之原型模式知识总结

    如何使用? 1.首先定义一个User类,它必须实现了Cloneable接口,重写了clone()方法. public class User implements Cloneable { private String name; private int age; private Brother brother; @Override protected Object clone() throws CloneNotSupportedException { return super.clone(); }

  • java数据结构算法稀疏数组示例详解

    目录 一.什么是稀疏数组 二.场景用法 1.二维数组转稀疏数组思路 2.稀疏数组转二维数组思路 3.代码实现 一.什么是稀疏数组 当一个数组a中大部分元素为0,或者为同一个值,那么可以用稀疏数组b来保存数组a. 首先,稀疏数组是一个数组,然后以一种特定的方式来保存上述的数组a,具体处理方法: 记录数组a一共有几行几列 记录a中有多少个不同的值 最后记录不同值的元素所在行列,以及具体的值,放在一个小规模的数组里,以缩小程序的规模. 这个小规模的数组,就是稀疏数组. 举个栗子,左侧是一个二维数组,一

  • Java数据结构之稀疏数组的实现与应用

    目录 1.稀疏数组引入 1.1 使用场景 1.2 稀疏数组简介 2.稀疏数组的实现 2.1 案例概述 2.2 思路分析 2.3 代码实现 1.稀疏数组引入 1.1 使用场景 笔者在课程设计中曾写过一个扫雷小游戏,为了便于讲解,我们来做个简化(实际比这个复杂),只考虑当前位置有雷与无雷两种状况:雷用1表示,非雷用0表示.则将当前状态用二维数组表示如下: 在右侧的二维数组中,很多都是0,即记录了很多没有意义的数据,因此,我们考虑使用稀疏数组进行存储结构的优化. 1.2 稀疏数组简介 当一个数组中的大

  • java数据结构基础:稀疏数组

    目录 稀疏数组: 实现思路: 举例: 二维数组转稀疏数组实现思路: 稀疏数组恢复二维数组实现思路: 代码实现: 输出结果: 总结 稀疏数组: 当一个二维数组中大部份的值为0,或者为同一值的时候,可以用稀疏数组来保存 实现思路: 记录二维数组有多少行多少列.多少个不同的值 把不同的值按照所在行列,记录在一个规模较小的数组中 举例: 11×11的二维数组: 对应的稀疏数组: 其中,第一行分别为,原二维数组总行数.总列数.不为0的数的个数 之后几行的每一列分别代表所在行.所在列.值 二维数组转稀疏数组

  • 浅谈java面向对象的数组化信息处理

    虽然非常简单的东西,但对于一些自学的新手和前期理解的不够深的萌新来说,应该会有很大的帮助,有助于理解. 初学面向对象的时候,我想许多同学对此很纳闷.简单的问题复杂化,多此一举诸之云云. 那么往下看: package cn.bdqn.test3; import java.util.Scanner; public class Test1 { public static void main(String[] args) { //创建两个管理员对象 Admin a1 = new Admin(); a1.

  • 浅谈Java中常用数据结构的实现类 Collection和Map

    线性表,链表,哈希表是常用的数据结构,在进行Java开发时,JDK已经为我们提供了一系列相应的类来实现基本的数据结构.这些类均在java.util包中.本文试图通过简单的描述,向读者阐述各个类的作用以及如何正确使用这些类. Collection ├List │├LinkedList │├ArrayList │└Vector │ └Stack └Set Map ├Hashtable ├HashMap └WeakHashMap Collection接口 Collection是最基本的集合接口,一个C

  • 浅谈Java自定义注解相关知识

    一.自定义注解格式 分析 Java 中自带的 @Override 注解 , 源码如下 : @Target(ElementType.METHOD) @Retention(RetentionPolicy.SOURCE) public @interface Override { } 注解分为两部分 : ① 元注解 ; ② public @interface 注解名称 ; 二.注解本质分析 按照 public @interface 注解名称 格式 , 写出一个注解 , 编译该注解代码生成 Annotat

  • 浅谈java 字符串,字符数组,list间的转化

    1.关于java.lang.string.split xxx.split()方法可以将一个字符串分割为子字符串,然后将结果作为字符串数组返回. 2.字符串转字符数组 String str =" aa.png,a2.png,a3.png"; String[] arrayStr =new String[]{}; arrayStr = str.split(","); 3.字符数组转list List list = java.util.Arrays.asList(array

随机推荐