
如果把一维数组比作一排带编号的储物柜那二维数组就是一个带行号和列号的货架。试想以下存储一个班 5 名学生、3 门课的成绩该怎么存定义 15 个变量显然不现实用一维数组也得定义 5 个还是麻烦。那有没有更简洁的办法答案就是——二维数组。它本质上就是“数组里的数组”可以帮我们轻松处理表格型数据。本文将从二维数组的基本概念入手讲解它的声明、初始化、遍历方式和常见应用场景。入门案例请用二维数组输出如下图形1 0 0 0 00 1 0 0 00 0 1 0 00 0 0 1 00 0 0 0 1//二维数组 public class TwoDimensionalArray01 { //编写一个main方法 public static void main(String[] args) { //创建二维数组 int[][] arr {{1, 0, 0, 0, 0}, {0, 1, 0, 0, 0}, {0, 0, 1, 0, 0}, {0, 0, 0, 1, 0}, {0, 0, 0, 0, 1}}; //关于二维数组的关键概念 //(1).二维数组里有 5 个 {}每个 {} 为一个元素 //(2).二维数组的每个元素是一维数组所以如果需要得到每个一维数组的值还需要再次遍历 //(3).如果我们要访问第 (i1) 个一维数组的 (j1) 个值arr[i][j] System.out.println(二维数组的元素个数 arr.length); //5 //打印图形 //arr.length 表示元素个数本题为 5 //arr[i].length 表示第 i 1 个元素数组的长度 for(int i 0; i arr.length; i) { for(int j 0; j arr[i].length; j) { //输出一维数组 System.out.print(arr[i][j]); if(j ! arr[i].length - 1) { System.out.print( ); } } System.out.println(); } /* 1 0 0 0 0 0 1 0 0 0 0 0 1 0 0 0 0 0 1 0 0 0 0 0 1 */ } }二维数组的使用方式(1). 动态初始化(2). 静态初始化动态初始化1语法类型[ ][ ] 数组名 new 类型[大小][大小];推荐也可以类型 数组名[ ][ ] new 类型[大小][大小];如int[ ][ ] arr new int[2][3]; 或 int arr new int[2][3];动态初始化2语法(1). 先声明类型[ ][ ] 数组名;也可以类型 数组名[ ][ ];(2). 再定义开辟空间数组名 new 类型[大小][大小];(3). 赋值有默认值比如 int 类型默认 0动态初始化3 -- 列数不确定语法语法可用动态初始化1 或 动态初始化 2区别在于new 类型[大小][ ]即第一个 [ ] 为空表示不确定大小以动态初始化1 为例类型[ ][ ] 数组名 new 类型[大小][ ];如int[][] arr new int[5][];表示该二维数组有 5 个一维数组每个一维数组还没有开辟数据空间注意不存在 new 类型[ ][大小]; 这样的写法二维数组的元素个数行数必须有一个明确值否则会报错静态初始化语法类型[ ][ ] 数组名 {{值1, 值2, ...}, {值1, 值2, ...}, {值1, 值2, ...}, ...};推荐也可以类型 数组名[ ][ ] {{值1, 值2, ...}, {值1, 值2, ...}, {值1, 值2, ...}, ...};如int[][] arr {{1, 1, 3}, {2, 5, 9}, {7}};定义了一个二维数组有 3 个元素每个元素都是一维数组前两个一维数组都有 3 个元素最后一个一维数组有 1 个元素注意不能写成 int[ ][ ] arr {{1, 1, 3}, {2, 5, 9},7}; 因为前两个元素都是一维数组是引用类型而第 3 个元素是一个数值是基本数据类型使得二维数组内部类型不匹配会出现报错二维数组的注意事项和使用细节1. 二维数组实际上是由多个一维数组组成的它的各个一维数组的长度可以相同也可以不同。如int[][] map {{1, 2}, {3, 4, 5}};由 map[0] 是一个含有两个元素的一维数组map[1] 是一个含有三个元素的一维数组构成该数组也可称为列数不等的二维数组2. 在二维数组在列数不确定的情况下行数必须有一个明确值定义二维数组时一维数组元素个数不能为空int[][] arr1 new int[5][]; //正确 int[][] arr2 new int[][5]; //错误二维数组练习练习一int[ ][ ] arr {{4, 6}, {1, 4, 5, 7}, {-2}}; 遍历该二维数组并得到和public class TwoDimensionalArrayExercise01 { //编写一个main方法 public static void main(String[] args) { int[][] arr {{4, 6}, {1, 4, 5, 7}, {-2}}; //遍历并求和 int sum 0; for(int i 0; i arr.length; i) { for(int j 0; j arr[i].length; j) { sum arr[i][j]; if(j ! arr[i].length - 1) { System.out.print(arr[i][j] ); } else { System.out.println(arr[i][j]); } } } System.out.println(和 sum); } /* 4 6 1 4 5 7 -2 和 25 */ }练习二使用二维数组打印一个 10 行的杨辉三角11 11 2 11 3 3 11 4 6 4 11 5 10 10 5 1......规律1. 第一行有 1 个元素第 n 行有 n 个元素2. 每一行的第一个元素和最后一个元素都是 13. 从第三行开始对于非第一个元素和最后一个元素的元素值为上一行同一列的元素值与上一行前一列的元素值的和即arr[row][column] arr[row - 1][column] arr[row - 1][column - 1];public class TwoDimensionalArrayExercise02 { //编写一个main方法 public static void main(String[] args) { //创建二维数组 int[][] yanghui new int[10][]; for(int i 0; i yanghui.length; i) { //给每个一维数组行开辟数据空间 yanghui[i] new int[i 1]; for(int j 0; j yanghui[i].length; j) { if(j 0 || j i) { yanghui[i][j] 1; } else { //核心规律 yanghui[i][j] yanghui[i-1][j-1] yanghui[i-1][j]; } } } //遍历输出 for(int i 0; i yanghui.length; i) { for(int j 0; j yanghui[i].length; j) { if(j ! yanghui[i].length - 1) { System.out.print(yanghui[i][j] ); } else { System.out.println(yanghui[i][j]); } } } } }小结二维数组是 Java 中一种重要的数据结构本质上是“数组的数组”适合存储表格型数据。以上介绍了二维数组的应用案例、使用方式、注意事项和使用细节以及少量的练习希望小伙伴们能理解其“行”与“列”的存储结构。二维数组的使用方式灵活多样可通过动态初始化和静态初始化创建。遍历时通常使用嵌套循环外层控制行内层控制列。需要注意的是二维数组的每一行长度可以不同可视为“不规则二维数组”使用时小心下标越界问题。二维数组的应用场景非常广泛如成绩管理、矩阵运算、游戏棋盘等。掌握它就是掌握了一种高效处理数据的方式。关于数组的综合练习练习一下面数组定义正确的有A. String[ ] strs {a, b, c};B. String[ ] strs {a, b, c};C. String[ ] strs new String{a, b, c};D. String[ ] strs new String[ ]{a, b, c};E. String[ ] strs new String[3]{a, b, c};分析(1). A、B 选项都为数组的静态初始化但 A 选项的内部元素为字符char 类型与 str 数组的 String 不同而 B 选项的内部元素为字符串String 类型。故 A 错误B 正确(2). C 选项将动态初始化和静态初始化混用不存在该初始化方式正确声明为 String[ ] strs {a, b, c}; 故 C 错误(3). D、E 选项在编译过程中D 选项是通过的而 E 选项编译出现错误如果动态初始化后面加上具体的元素就不能在动态初始化时给出具体的长度。故 D 正确E 错误综上正确答案为 B, D练习二已知有个升序的数组要求插入一个元素该数组顺序依然是升序比如int[ ] num {10, 12, 45, 90}; 添加 23 元素后数组为 int[ ] num {10, 12, 23, 45, 90};public class ArrayExercise02 { //编写一个main方法 public static void main(String[] args) { //创建数组 num int[] num {10, 12, 45, 90}; int insert_num 23; //要插入的元素 int insert_Index 0; //要插入的位置索引 //确定插入的位置索引 for(int i 0; i num.length; i) { if(num[i] insert_num) { insert_Index i; break; } } //创建新数组 num2表示插入后的数组 int num2[] new int[num.length 1]; for(int i 0; i num2.length; i) { //值传递 if(i insert_Index) { num2[i] num[i]; } else if(i insert_Index) { num2[i] insert_num; } else { num2[i] num[i - 1]; } } //将 num2 赋给 num引用传递 num num2; //遍历输出 System.out.print(插入后的数组为 int[] num {); for(int i 0; i num.length; i) { if(i ! num.length - 1) { System.out.print(num[i] , ); } else { System.out.print(num[i] };); } } } //插入后的数组为 int[] num {10, 12, 23, 45, 90}; }练习三随机生成 10 个整数1-100的范围保存到数组并倒序打印并求平均值求最大值和最大值的下标并查找里面是否有元素 8public class ArrayExercise03 { //编写一个main方法 public static void main(String[] args) { //创建数组大小为 10 int[] arr new int[10]; int found_8 0; //判断是否有元素 8 int max 0; //最大值 int maxIndex 0; //最大值的下标 double average 0; //平均值 int add 0; //累积 for(int i 0; i arr.length; i) { //随机生成 1-100 的数字 arr[i] (int)(Math.random() * 100) 1; //判断是否存在元素 8 if(arr[i] 8) { found_8 1; } //确定最大值及其下标 if(arr[i] max) { max arr[i]; maxIndex i; } //累积 add arr[i]; } //遍历 System.out.println(arr 的元素情况 ); for(int i 0; i arr.length; i) { System.out.print(arr[i] ); } System.out.println(); //倒序遍历 System.out.println(arr 元素情况倒序); for(int i arr.length - 1; i 0; i--) { System.out.print(arr[i] ); } System.out.println(); //计算平均值 average (double)add / arr.length; System.out.println(该数组的平均数为 average); System.out.println(该数组的最大值为 max 最大值下标为 maxIndex); if(found_8 1) { System.out.println(该数组里有8); } else { System.out.println(该数组里没有8); } } }练习四试写出下列代码的输出结果public class ArrayExercise04 { //编写一个main方法 public static void main(String[] args) { char[] arr1 {a, z, b, c}; char[] arr2 arr1; arr1[2] 橙; for(int i 0; i arr2.length; i) { System.out.println(arr1[i] , arr2[i]); } } }分析首先定义字符数组 arr1然后创建新的字符数组 arr2并将 arr1 赋给 arr2由上篇数组所讲述的知识点得知此赋值为引用传递即 arr1 和 arr2 指向堆中同一个地址故 arr[2] 橙元素值传递后arr2[2] 也应为 橙故输出结果为a,az,z橙,橙c,c有关数组的相关内容自此已全部结束从一维数组的查找、排序和传递到二维数组的声明与使用掌握数组就是掌握了数据存储与操作的基本功。它不仅是后续学习集合框架的前提更是理解算法与数据结构的起点。后续我们来聊聊类与对象的相关内容我们下期见