Java数组(二)

Java数组(二)

1、多维数组

  • 多维数组可以看成是数组的数组,比如二维数组就是一个特殊的一维数组,其每一个元素都是一个一维数组。
  • 二维数组
int a[][] = new int[2][5];

解析:以上二维数组a可以看成一个两行五列的数组。

画图理解

在这里插入图片描述

可以理解为一维数组是一个线,每个元素是线上的一个点,二维数组是一个面,此时,每个元素依旧是面上的一个点,相对于线,你就需要有两个坐标去确定它

思考:多维数组的使用?

package com.xxsml.array;

public class ArrayDemo05 {
    public static void main(String[] args) {
        //[4][2]
        /*
            1,2  array[0]
            2,3  array[1]
            3,4  array[2]
            4,5  array[3]
         */
        int[][] array = {{1,2},{2,3},{3,4},{4,5}};

        System.out.println("=====输出外层数组长度=====");
        System.out.println(array.length);
        System.out.println("=====输出array[0]数组长度=====");
        System.out.println(array[0].length);
        System.out.println("=====直接输出array[0]=====");
        System.out.println(array[0]);  //[I@1540e19d  输出地址的原因因为array[0]代表的是{1,2}
        System.out.println("=====输出array[0][0]的值=====");
        System.out.println(array[0][0]);
        System.out.println("=====输出array[0][1]的值=====");
        System.out.println(array[0][1]);
        System.out.println("=====循环输出外层内层数组的长度=====");
        for (int i = 0; i < array.length; i++) {
            for (int j = 0; j < array[i].length; j++) {
                System.out.println(array[i][j]);
            }
        }
    }
}

输出结果

=====输出外层数组长度=====
4
=====输出array[0]数组长度=====
2
=====直接输出array[0]=====
[I@1540e19d
=====输出array[0][0]的值=====
1
=====输出array[0][1]的值=====
2
=====循环输出外层内层数组的长度=====
1
2
2
3
3
4
4
5

2、Arrays类

  • 数组的工具类java.util.Arrays
  • 由于数组对象本身并没有什么方法可以供我们调用,但API中提供了一个工具类Arrays供我们使用,从而可以对数据对象进行一些基本的操作。
  • 查看JDK帮助文档
  • Arrays类中的方法都是static修饰的静态方法,在使用的时候可以直接使用类名进行调用,而"不用"使用对象来调用(注意:是"不用”而不是“不能")
  • 具有以下常用功能:
    • 给数组赋值:通过fill方法。
    • 对数组排序:通过sot方法,按升序。
    • 比较数组:通过equals方法比较数组中元素值是否相等。
    • 查找数组元素:通过binarySearch方法能对排序好的数组进行二分查找法操作。

例1:

package com.xxsml.array;

import java.util.Arrays;

public class ArrayDemo06 {
    public static void main(String[] args) {
        int[] a = {1,2,54,34,6,4,3,43,3,5,867};

        //打印数组元素Arrays.toString
        System.out.println(Arrays.toString(a));

        //数组进行排序:升序
        Arrays.sort(a);
        System.out.println(Arrays.toString(a));

        //2~4用填充
        Arrays.fill(a,2,4,0);
        System.out.println(Arrays.toString(a));

        //数组填充
        Arrays.fill(a,0);
        System.out.println(Arrays.toString(a));
    }
}

输出结果

[1, 2, 54, 34, 6, 4, 3, 43, 3, 5, 867]
[1, 2, 3, 3, 4, 5, 6, 34, 43, 54, 867]
[1, 2, 0, 0, 4, 5, 6, 34, 43, 54, 867]
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]

toString是说以字符串的形式表示出来

总结和拓展

  1. 转换为字符串(Converting to String)Arrays.toString() 方法用于将数组转换为字符串,便于打印输出。

    java复制代码int[] arr = {1, 2, 3};
    System.out.println(Arrays.toString(arr));  // 输出:[1, 2, 3]
    
  2. 排序(Sorting)Arrays.sort() 方法用于对数组进行排序。默认情况下,它会按升序排序数组元素。

    java复制代码int[] arr = {3, 1, 4, 2};
    Arrays.sort(arr);
    System.out.println(Arrays.toString(arr));  // 输出:[1, 2, 3, 4]
    
  3. 填充(Filling)Arrays.fill() 方法用指定的值填充数组的所有元素。

    java复制代码int[] arr = new int[5];
    Arrays.fill(arr, 10);
    System.out.println(Arrays.toString(arr));  // 输出:[10, 10, 10, 10, 10]
    
  4. 复制(Copying)Arrays.copyOf() 方法用于复制数组。可以指定要复制的长度。

    java复制代码int[] source = {1, 2, 3, 4, 5};
    int[] target = Arrays.copyOf(source, 3);
    System.out.println(Arrays.toString(target));  // 输出:[1, 2, 3]
    
  5. 比较(Comparing)Arrays.equals() 方法用于比较两个数组是否相等。

    java复制代码int[] arr1 = {1, 2, 3};
    int[] arr2 = {1, 2, 3};
    System.out.println(Arrays.equals(arr1, arr2));  // 输出:true
    
  6. 搜索(Searching)Arrays.binarySearch() 方法用于在排序数组中搜索指定的元素。如果找到了该元素,则返回其索引;否则返回负数。

    java复制代码int[] arr = {1, 2, 3, 4};
    int index = Arrays.binarySearch(arr, 3);
    System.out.println("Index of 3: " + index);  // 输出:2
    

3、冒泡排序

冒泡排序无疑是最为出名的排序算法之一,总共有八大排序!

  • 冒泡的代码还是相当简单的,两层循济,外层冒泡轮数,里层依次比较,江湖中人人尽皆知。

  • 我们看到嵌套循环,应该立马就可以得出这个算法的时间复杂度为O(2)。

  • 冒泡排序

    1. 比较数组中,两个相邻的元素,如果第一个数比第二个数大,我们就交换他们的位置;
    2. 每一次比较,都会产生出一个最大,或者最小的数字;
    3. 下一轮则可以少一次排序!
    4. 依次循环,直到结束!
package com.xxsml.array;

import java.util.Arrays;

public class ArrayDemo07 {
    public static void main(String[] args) {
        int[] a = {1,3,43,5,63,2,54,28,6,12,43,22};

        //调用完我们自己写的排序方法以后,返回一个排序后的数组
        int[] sort = sort(a);

        System.out.println(Arrays.toString(sort));
    }
    public static int[] sort(int[] array){
        //临时变量
        int temp = 0;

        //外层循环,判断我们这个要走多少次
        for (int i = 0;i < array.length - 1;i++){
            //内层循环:比较这两个数,如果后一个大于前面一个,则交换位置
            for (int j = 0; j < array.length - 1 - i; j++) {
                if (array[j+1]>array[j]){
                    temp = array[j];
                    array[j] = array[j+1];
                    array[j+1] = temp;
                }
            }
        }
        return array;
    }
}

输出结果

[63, 54, 43, 43, 28, 22, 12, 6, 5, 3, 2, 1]

思考:如何优化?

package com.xxsml.array;

import java.util.Arrays;

public class ArrayDemo07 {
    public static void main(String[] args) {
        int[] a = {1,3,43,5,63,2,54,28,6,12,43,22};

        //调用完我们自己写的排序方法以后,返回一个排序后的数组
        int[] sort = sort(a);

        System.out.println(Arrays.toString(sort));
    }
    public static int[] sort(int[] array){
        //临时变量
        int temp = 0;

        //外层循环,判断我们这个要走多少次
        for (int i = 0;i < array.length - 1;i++){
            boolean flag = false; //通过flag标识位减少没有意义的比较
            //内层循环:比较这两个数,如果后一个大于前面一个,则交换位置
            for (int j = 0; j < array.length - 1 - i; j++) {
                if (array[j+1]>array[j]){
                    temp = array[j];
                    array[j] = array[j+1];
                    array[j+1] = temp;
                    flag = true;
                }
            }
            if(flag == false){
                break;
            }
        }
        return array;
    }
}

修改位置:第20行:boolean flag = false; //通过flag标识位减少没有意义的比较

第30~32行:

if(flag == false){
break;
}

第二段代码相对于第一段代码在性能上进行了优化,具体优化点在于使用了一个boolean类型的flag变量来减少不必要的比较。这是经典的冒泡排序算法的一个改进。

优化点如下:

  1. 减少不必要的比较:在冒泡排序中,如果某一趟遍历过程中没有进行任何交换(即数组已经有序或局部有序),那么之后的遍历将不会改变数组的顺序。因此,在第二段代码中,如果在某一趟遍历中没有发生交换(即flag仍为false),则直接跳出内层循环,结束这一趟的遍历。
  2. 时间复杂度的潜在降低:虽然冒泡排序的最坏时间复杂度仍然是O(n^2),但使用flag变量后,当数组已经有序或大部分有序时,算法会提前结束,从而减少了一些不必要的比较和交换操作,提高了效率。

当数组已经有序时,第一段代码仍然会进行完整的n-1趟遍历,而第二段代码在第一趟遍历后就会检测到没有发生交换,从而直接结束排序。

第二段代码通过引入flag变量来减少不必要的比较,提高了冒泡排序算法在数组已经有序或大部分有序时的性能。这是一个有效的优化,虽然不改变算法的最坏时间复杂度,但在实际应用中可能会带来显著的性能提升。

4、稀疏数组

需求:编写五子棋游戏中,有存盘退出和续上盘的功能。

在这里插入图片描述

分析问题:因为该二维数组的很多值是默认值0,因此记录了很多没有意义的数据。
解决:稀疏数组

稀疏数组介绍

  • 当一个数组中大部分元素为0,或者为同一值的数组时,可以使用稀疏数组来保存该数组。
  • 稀硫数组的处理方式是:
    • 记录数组一共有几行几列,有多少个不同值
    • 把具有不同值的元素和行列及值记录在一个小规模的数组中,从而缩小程序的规模
  • 如下图:左边是原始数组,右边是稀疏数组

在这里插入图片描述

数组的应用

package com.xxsml.array;

public class ArrayDemo08 {
    public static void main(String[] args) {
        //1、创建一个二维数组 11*11 0:没有棋子 1:黑棋 2:白棋
        int[][] array1 = new int[11][11];
        array1[1][2] = 1;
        array1[2][3] = 2;
        //输出原始数组
        System.out.println("输出原始数组");

        for (int[] ints : array1) {
            for (int anInt : ints) {
                System.out.print(anInt+"  ");
            }
            System.out.println();
        }

        System.out.println("=============");
        //转换为稀疏数组保存
        //获取有效值的个数
        int sum = 0;
        for (int i = 0; i < 11; i++) {
            for (int j = 0; j < 11; j++) {
                if (array1[i][j] != 0){
                    sum++;
                }
            }
        }
        System.out.println("有效值的个数:"+sum);

        //2、创建一个稀疏数组的数组
        int[][] array2 = new int[sum+1][3];
        array2[0][0] = 11;
        array2[0][1] = 11;
        array2[0][2] = sum;  //把稀疏数组的头(第一行)打出来了

        //遍历二维数组,将非零的值,存放稀疏数组中
        int count = 0;
        for (int i = 0; i < array1.length; i++) {
            for (int j = 0; j < array1[i].length; j++) {
                if (array1[i][j] != 0){
                    count++;
                    //把第2至最后一行也打出来了
                    array2[count][0] = i;  //第count行的第1个数存它的横坐标
                    array2[count][1] = j;  //第count行的第2个数存它的纵坐标
                    array2[count][2] = array1[i][j];  //第count行的第3个数存它的值
                }
            }
        }

        //输出稀疏数组
        for (int i = 0; i < array2.length; i++) {
            System.out.println(array2[i][0]+"  "
                              +array2[i][1]+"  "
                              +array2[i][2]+"  ");
        }

        System.out.println("=============");
        System.out.println("还原为原始的数组");
        //1、读取叙述数组的值
        int[][] array3 = new int[array2[0][0]][array2[0][1]]; //行为array2[0][0],列为array2[0][1]

        //2、给其中的元素还原值
        for (int i = 1; i < array2.length; i++) {
            array3[array2[i][0]][array2[i][1]] = array2[i][2]; //array2[i][0]为这个数的横坐标,array2[i][1]为这个数的纵坐标,array2[i][2]为这个数的值
        }

        //3、打印还原数组
        System.out.println("输出还原的数组");

        for (int[] ints : array3) {
            for (int anInt : ints) {
                System.out.print(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  
=============
有效值的个数:2
11  11  2  
1  2  1  
2  3  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  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

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/613109.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

Spring、SpringMVC

一、Spring框架中的单例Bean是线程安全的吗&#xff1f; 【默认单例的情况下】Spring Bean并没有可变的状态&#xff08;如Service类和DAO类&#xff09;&#xff0c;即只能查不能改&#xff0c;所以没有并发问题&#xff0c;所以某种程度上来说Spring的单例Bean是线程安全的。…

mybatis 跨库查询 mysql

跨库&#xff0c;表关联的查询&#xff0c;实现起来很简单&#xff1a; select a.uid from ucenter.user a , database user_profile b where a.uid b.uid;只要在表的前边加上库名即可。 这个是我项目中xml 中的一个例子&#xff0c;项目采用的是springmvc,持久层框架就是my…

怎么在电脑上设置提醒事项,并显示在桌面上?

有时候&#xff0c;生活的琐碎与工作的繁忙交织成一张巨大的网&#xff0c;让我在其中穿梭而时常感到力不从心。那次重要的会议&#xff0c;我竟然忘记了准备资料&#xff0c;尴尬地站在会议室门口&#xff0c;心跳如鼓&#xff0c;那种因为遗忘而产生的挫败感&#xff0c;仿佛…

Android Studio 查看打开Room数据库数据

关于作者&#xff1a; CSDN内容合伙人、技术专家&#xff0c; 从零开始做日活千万级APP&#xff0c;带领团队单日营收超千万。 专注于分享各领域原创系列文章 &#xff0c;擅长java后端、移动开发、商业化变现、人工智能等&#xff0c;希望大家多多支持。 目录 一、导读二、概览…

Web界面加持!数据库备份神器,助你轻松备份数据!

使用这款带有Web界面的数据库备份神器&#xff0c;你可以轻松设置定时备份&#xff0c;确保数据安全无忧。备份结果即时通知&#xff0c;让你随时掌握备份状态。备份完成后&#xff0c;你将收到备份结果通知。无论是成功备份还是出现错误&#xff0c;你都能及时了解备份情况&am…

DRF 纯净版创建使用

【一】介绍 &#xff08;1&#xff09;使用原因 在Django中&#xff0c;contrib 包包含了许多内置的app和中间件&#xff0c;如auth、sessions、admin等&#xff0c;这些app在创建新的Django项目时默认是包含在内的。然而&#xff0c;在开发RESTful API时&#xff0c;可能不需…

使用vant-ui+vue3实现一个可复用的评星组件

如图所示 有两种情况 一种是5颗星 一种是3颗星 官网上只提供了图标类型的 并没有加文字 https://femessage-vant.netlify.app/#/zh-CN/ 自己结合两种情况 在全局注册了此组件(后续还会持续更新代码~) <template><div class"vant_rate_wrapper"><van…

requestAnimationFrame请求动画帧

一、前言 在Web应用中&#xff0c;实现动画效果的方法比较多&#xff1a; CSS3&#xff1a;Transition&#xff08;过度&#xff09; / Animation&#xff08;动画&#xff09; HTML5&#xff1a;Canvas JavaScript&#xff1a;setInterval&#xff08;定时器&#xff09; /…

2010年认证杯SPSSPRO杯数学建模D题(第一阶段)服务网点的分布全过程文档及程序

2010年认证杯SPSSPRO杯数学建模 D题 服务网点的分布 原题再现&#xff1a; 服务网点、通讯基站的设置&#xff0c;都存在如何设置较少的站点&#xff0c;获得较大效益的问题。通讯基站的覆盖范围一般是圆形的&#xff0c;而消防、快餐、快递服务则受到道路情况和到达时间的限…

答辩PPT制作太费时?AI工具帮你节省时间

在我原本的认知里面&#xff0c;答辩PPT是要包含论文各个章节的&#xff0c;在答辩时需要方方面面都讲到的&#xff0c;什么摘要、文献综述、实证分析、研究结果样样不落。但是&#xff0c;这大错特错&#xff01; 答辩PPT环节时长一般不超过5分钟&#xff0c;老师想要的答辩P…

2024美国虚拟信用卡申请流程

一、消费场景 二、如果申请 Fomepay美国虚拟信用卡 1.打开 Fomepay官方网站地址 2、登录之后根据自己的需求选择卡bin 3、点击申请卡&#xff0c;选择金额、填写姓名&#xff0c;选择微信/支付宝点击确认开卡即可 记得刷新页面哦~~~~~ 卡信息在卡中心cvc安全码里面 4、虚拟信…

DRF渲染之异常处理

异常处理 【1 】引言 Django REST Framework 这个就是我们常常说的DRF APIView的dispatch方法&#xff1a; 当请求到达视图时&#xff0c;DRF 的 APIView 类会调用 dispatch 方法来处理请求。在 dispatch 方法中&#xff0c;有一个关键的步骤是处理异常。如果在视图类的方法…

mikefile函数与实用模板

文章目录 0.概述1.函数调用语法2.字符串处理函数2.1 subst&#xff08;字符串替换函数&#xff09;2.2 patsubst&#xff08;模式字符串替换函数&#xff09;2.3 strip&#xff08;去空格函数&#xff09;2.4 findstring&#xff08;查找字符串函数&#xff09;2.5 filter&…

Aigtek:电压放大器的选型标准是什么

选型电压放大器时&#xff0c;需要考虑多个因素&#xff0c;以确保选择适合特定应用需求的设备。电压放大器该怎么选择&#xff0c;下面安泰电子来介绍电压放大器常见的选型标准。 增益要求&#xff1a;首先需要确定所需的增益水平。根据输入信号的幅度和输出信号的要求&#x…

只需3步,使用Stable Diffusion无限生成AI数字人视频(附安装包)

基本方法 搞一张照片&#xff0c;搞一段语音&#xff0c;合成照片和语音&#xff0c;同时让照片中的人物动起来&#xff0c;特别是头、眼睛和嘴。 语音合成 语音合成的方法很多&#xff0c;也比较成熟了&#xff0c;大家可以选择自己方便的&#xff0c;直接录音也可以&#…

【ZZULI数据结构实验】压缩与解码的钥匙:赫夫曼编码应用

&#x1f4c3;博客主页&#xff1a; 小镇敲码人 &#x1f49a;代码仓库&#xff0c;欢迎访问 &#x1f680; 欢迎关注&#xff1a;&#x1f44d;点赞 &#x1f442;&#x1f3fd;留言 &#x1f60d;收藏 &#x1f30f; 任尔江湖满血骨&#xff0c;我自踏雪寻梅香。 万千浮云遮碧…

大文件传输的好帮手Libarchive:功能强大的开源归档文件处理库

在数字化时代&#xff0c;文件的存储和传输对于企业的日常运作至关重要。但是&#xff0c;服务器中的压缩文件往往无法直接查看或预览&#xff0c;这给用户带来了不便。为了解决这一问题&#xff0c;在线解压功能的开发变得尤为重要。接下来&#xff0c;小编将介绍一个能够实现…

了解集合与数据结构(java)

什么是数据结构? 数据结构就是 数据结构, 功能就是描述和组织数据 比如我有10万个QQ号, 我来组织, 有很多种组织方法, 比如链表, 树, 堆, 栈等等. 假如QQ号要查找数据, 有种数据结构查找数据速度很快, 我们就用它 加入QQ号要进行删除数据, 有种数据结构删除速度很快, 我们…

Spring Cloud Alibaba 网关 Gateway 集成(7)

项目的源码地址 Spring Cloud Alibaba 工程搭建&#xff08;1&#xff09; Spring Cloud Alibaba 工程搭建连接数据库&#xff08;2&#xff09; Spring Cloud Alibaba 集成 nacos 以及整合 Ribbon 与 Feign 实现负载调用&#xff08;3&#xff09; Spring Cloud Alibaba Ribbo…

【Web】CTFSHOW 月饼杯 题解(全)

目录 web1_此夜圆 web2_故人心 web3_莫负婵娟 web1_此夜圆 拿到源码&#xff0c;一眼字符串逃逸 本地测一测&#xff0c;成功弹出计算器 <?phpclass a {public $uname;public $password;public function __wakeup(){system(calc);} }function filter($string){retur…