简介

二维数组:本质上就是元素为一维数组的一个数组
二维数组的标记:[][]

  1. int[][] arr; //arr是一个二维数组,可以看成元素是int[]一维数组类型的一个数组

二维数组的声明与初始化

语法格式

//推荐
元素的数据类型[][] 二维数组的名称;
int[][] arr;

//不推荐
元素的数据类型  二维数组名[][];
int arr[][];
//不推荐
元素的数据类型[]  二维数组名[];
int[] arr[];

面试

int[] x, y[];
//x是一维数组,y是二维数组

静态初始化

元素的数据类型[][] 二维数组名 = new 元素的数据类型[][]{
            {元素1,元素2,元素3 。。。}, 
            {第二行的值列表},
            ...
            {第n行的值列表}
        };

元素的数据类型[][] 二维数组名;
二维数组名 = new 元素的数据类型[][]{
            {元素1,元素2,元素3 。。。}, 
            {第二行的值列表},
            ...
            {第n行的值列表}
        };

//以下格式要求声明与静态初始化必须一起完成
元素的数据类型[][] 二维数组的名称 = {
            {元素1,元素2,元素3 。。。}, 
            {第二行的值列表},
            ...
            {第n行的值列表}
        };

如果是静态初始化,右边**new 数据类型[][]**中不能写数字,因为行数和列数,由 {} 的元素个数决定

举例

int[][] arr;
arr = new int[][]{{1,2,3},{4,5,6},{7,8,9}};
arr = new int[3][3]{{1,2,3},{4,5,6},{7,8,9}};//错误,静态初始化右边new 数据类型[]中不能写数字

int[][] arr = new int[][]{{1,2,3},{4,5,6},{7,8,9}};

int[][] arr = {{1,2,3},{4,5,6},{7,8,9}};//声明与初始化必须在一句完成
public class Array2Demo1 {
    public static void main(String[] args) {
        //定义数组
        int[][] arr = {{1,2,3},{4,5},{6}};

        System.out.println(arr);
        System.out.println(arr[0]);
        System.out.println(arr[1]);
        System.out.println(arr[2]);

        System.out.println(arr[0][0]); //1
        System.out.println(arr[1][0]); //4
        System.out.println(arr[2][0]); //6

        System.out.println(arr[0][1]); //2
        System.out.println(arr[1][1]); //5
        //越界
        System.out.println(arr[2][1]); //错误
    }
}

动态初始化(规则二维表:每一行的列数是相同的)

//(1)确定行数和列数
元素的数据类型[][] 二维数组名 = new 元素的数据类型[m][n];
    m:表示这个二维数组有多少个一维数组。或者说一共二维表有几行
    n:表示每一个一维数组的元素有多少个。或者说每一行共有一个单元格

//此时创建完数组,行数、列数确定,而且元素也都有默认值

//(2)再为元素赋新值
二维数组名[行下标][列下标] = 值;
public static void main(String[] args) {
    //定义一个二维数组
    int[][] arr = new int[3][2];

    //定义了一个二维数组arr
    //这个二维数组有3个一维数组的元素
    //每一个一维数组有2个元素
    //输出二维数组名称
    System.out.println(arr); //地址值    [[I@175078b

    //输出二维数组的第一个元素一维数组的名称
    System.out.println(arr[0]); //地址值    [I@42552c
    System.out.println(arr[1]); //地址值    [I@e5bbd6
    System.out.println(arr[2]); //地址值    [I@8ee016

    //输出二维数组的元素
    System.out.println(arr[0][0]); //0
    System.out.println(arr[0][1]); //0

    //...
}

动态初始化(不规则:每一行的列数可能不一样)

//(1)先确定总行数
元素的数据类型[][] 二维数组名 = new 元素的数据类型[总行数][];

//此时只是确定了总行数,每一行里面现在是null

//(2)再确定每一行的列数,创建每一行的一维数组
二维数组名[行下标] = new 元素的数据类型[该行的总列数];

//此时已经new完的行的元素就有默认值了,没有new的行还是null

//(3)再为元素赋值
二维数组名[行下标][列下标] = 值;
    public static void main(String[] args) {
        //定义数组
        int[][] arr = new int[3][];

        System.out.println(arr);    //[[I@175078b

        System.out.println(arr[1][0]);//NullPointerException
        System.out.println(arr[0]); //null
        System.out.println(arr[1]); //null
        System.out.println(arr[2]); //null

        //动态的为每一个一维数组分配空间
        arr[0] = new int[2];
        arr[1] = new int[3];
        arr[2] = new int[1];

        System.out.println(arr[0]); //[I@42552c
        System.out.println(arr[1]); //[I@e5bbd6
        System.out.println(arr[2]); //[I@8ee016

        System.out.println(arr[0][0]); //0
        System.out.println(arr[0][1]); //0
        //ArrayIndexOutOfBoundsException
        //System.out.println(arr[0][2]); //错误

        arr[1][0] = 100;
        arr[1][2] = 200;
    }

二维数组的遍历

for(int i=0; i<二维数组名.length; i++){
    for(int j=0; j<二维数组名[i].length; j++){
        System.out.print(二维数组名[i][j]);
    }
    System.out.println();
}

数组操作的常见异常

数组越界异常

public static void main(String[] args) {
    int[] arr = {1,2,3};
    System.out.println(arr[3]);
}

创建数组,赋值3个元素,数组的索引就是0,1,2,没有3索引,因此不能访问数组中不存在的索引,程序运行后,将会抛出 ArrayIndexOutOfBoundsException 数组越界异常;在开发中,数组的越界异常是不能出现的,一旦出现了,就必须要修改编写的代码
数组越界异常.jpg
¡

数组空指针异常

    public static void main(String[] args) {
        //定义数组
        int[][] arr = new int[3][];

        System.out.println(arr[0][0]);//NullPointerException
    }

因为此时数组的每一行还未分配具体存储元素的空间,此时arr[0]是null,此时访问arr[0][0]会抛出NullPointerException 空指针异常。空指针异常.jpg

空指针异常在内存图中的表现
1572338767825.png

二维数组练习

练习1

请使用二维数组存储如下数据,并遍历显示
1
2 2
3 3 3
4 4 4 4
5 5 5 5 5

    public static void main(String[] args){
        //1、声明一个二维数组,并且确定行数
        //因为每一行的列数不同,这里无法直接确定列数
        int[][]  arr = new int[5][];

        //2、确定每一行的列数
        for(int i=0; i<arr.length; i++){
            /*
            arr[0] 的列数是1
            arr[1] 的列数是2
            arr[2] 的列数是3
            arr[3] 的列数是4
            arr[4] 的列数是5
            */
            arr[i] = new int[i+1];
        }

        //3、确定元素的值
        for(int i=0; i<arr.length; i++){
            for(int j=0; j<arr[i].length; j++){
                arr[i][j] = i+1;
            }
        }

        //4、遍历显示
        for(int i=0; i<arr.length; i++){
            for(int j=0; j<arr[i].length; j++){
                System.out.print(arr[i][j] + " ");
            }
            System.out.println();
        }

    }
    public static void main(String[] args){
        //1、声明一个二维数组,并且初始化
        int[][] arr = {
            {1},
            {2,2},
            {3,3,3},
            {4,4,4,4},
            {5,5,5,5,5}
        };


        //2、遍历显示
        for(int i=0; i<arr.length; i++){
            for(int j=0; j<arr[i].length; j++){
                System.out.print(arr[i][j] + " ");
            }
            System.out.println();
        }

    }
    public static void main(String[] args){
        //1、声明一个二维数组,并且确定行数
        //因为每一行的列数不同,这里无法直接确定列数
        int[][]  arr = new int[5][];


        for(int i=0; i<arr.length; i++){
            //2、确定每一行的列数
            arr[i] = new int[i+1];

            //3、确定元素的值
            for(int j=0; j<arr[i].length; j++){
                arr[i][j] = i+1;

                System.out.print(arr[i][j] + " ");
            }

            System.out.println();
        }

    }

练习2

请使用二维数组存储如下数据,并遍历显示
1 1 1 1 1
2 2 2 2 2
3 3 3 3 3
4 4 4 4 4

public static void main(String[] args){
        int[][] arr = {
            {1,1,1,1,1},
            {2,2,2,2,2},
            {3,3,3,3,3},
            {4,4,4,4,4}
        };

        for(int i=0; i<arr.length; i++){
            for(int j=0; j<arr[i].length; j++){
                System.out.print(arr[i][j]+" ");
            }
            System.out.println();
        }
    }
    public static void main(String[] args) {
        //1、声明二维数组,并确定行数和列数
        int[][] arr = new int[4][5];

        //2、确定元素的值
        for (int i = 0; i < arr.length; i++) {
            for (int j = 0; j < arr.length; j++) {
                arr[i][j] = i + 1;
            }
        }

        //3、遍历显示
        for(int i=0; i<arr.length; i++){
            for(int j=0; j<arr[i].length; j++){
                System.out.print(arr[i][j] + " ");
            }
            System.out.println();
        }
    }

练习3

请使用二维数组存储如下数据,并遍历显示

        String[][] employees = {
                {"10", "1", "段誉", "22", "3000"},
                {"13", "2", "令狐冲", "32", "18000", "15000", "2000"},
                {"11", "3", "任我行", "23", "7000"},
                {"11", "4", "张三丰", "24", "7300"},
                {"12", "5", "周芷若", "28", "10000", "5000"},
                {"11", "6", "赵敏", "22", "6800"},
                {"12", "7", "张无忌", "29", "10800","5200"},
                {"13", "8", "韦小宝", "30", "19800", "15000", "2500"},
                {"12", "9", "杨过", "26", "9800", "5500"},
                {"11", "10", "小龙女", "21", "6600"},
                {"11", "11", "郭靖", "25", "7100"},
                {"12", "12", "黄蓉", "27", "9600", "4800"}
            };

其中”10”代表普通职员,”11”代表程序员,”12”代表设计师,”13”代表架构师
1561529559251.png

    public static void main(String[] args) {
        String[][] employees = {
                {"10", "1", "段誉", "22", "3000"},
                {"13", "2", "令狐冲", "32", "18000", "15000", "2000"},
                {"11", "3", "任我行", "23", "7000"},
                {"11", "4", "张三丰", "24", "7300"},
                {"12", "5", "周芷若", "28", "10000", "5000"},
                {"11", "6", "赵敏", "22", "6800"},
                {"12", "7", "张无忌", "29", "10800","5200"},
                {"13", "8", "韦小宝", "30", "19800", "15000", "2500"},
                {"12", "9", "杨过", "26", "9800", "5500"},
                {"11", "10", "小龙女", "21", "6600"},
                {"11", "11", "郭靖", "25", "7100"},
                {"12", "12", "黄蓉", "27", "9600", "4800"}
            };
        System.out.println("员工类型\t编号\t姓名\t年龄\t薪资\t奖金\t股票\t");
        for (int i = 0; i < employees.length; i++) {
            switch(employees[i][0]){
            case "10":
                System.out.print("普通职员");
                break;
            case "11":
                System.out.print("程序员");
                break;
            case "12":
                System.out.print("设计师");
                break;
            case "13":
                System.out.print("架构师");
                break;
            }
            for (int j = 1; j < employees[i].length; j++) {
                System.out.print("\t" + employees[i][j]);
            }
            System.out.println();
        }
    }

二维数组的内存图分析

示例一

int[][] arr = {
    {1},
    {2,2},
    {3,3,3},
    {4,4,4,4},
    {5,5,5,5,5}
};

1562112672215.png

示例二

//1、声明二维数组,并确定行数和列数
int[][] arr = new int[4][5];

//2、确定元素的值
for (int i = 0; i < arr.length; i++) {
    for (int j = 0; j < arr.length; j++) {
        arr[i][j] = i + 1;
    }
}

1562113179785.png

示例三

//1、声明一个二维数组,并且确定行数
//因为每一行的列数不同,这里无法直接确定列数
int[][]  arr = new int[5][];

//2、确定每一行的列数
for(int i=0; i<arr.length; i++){
    /*
    arr[0] 的列数是1
    arr[1] 的列数是2
    arr[2] 的列数是3
    arr[3] 的列数是4
    arr[4] 的列数是5
    */
    arr[i] = new int[i+1];
}

//3、确定元素的值
for(int i=0; i<arr.length; i++){
    for(int j=0; j<arr[i].length; j++){
        arr[i][j] = i+1;
    }
}

1562113981079.png