第9章 数组(随笔)

数组是一组相同数据类型元素的集合。在Java中数组属于引用类型,即数组是一个对象。

1. 一维数组

一维数组的定义

一维数组的两种声明方式:

数组元素类型 数组名字[];

数组元素类型[] 数组名字;  //推荐使用

这种方式声明数组时并未给数组分配内存,因此还不能直接使用,需要使用构造函数new方法为数组分配内存,语法如下:

数组元素类型  数组名 = new 数组元素类型[数组元素个数]

eg:

int week[] = new int[7];

上面的代码创建了数组week,并指定数组长度为7,使用new关键字为数组分配内存时,整型数组中各个元素的初始值为0.

一维数组的初始化

有以下几种方式初始化一维数组

  • 使用 new 指定数组大小后进行初始化
  • 使用 new 指定数组元素的值
  • 直接指定数组元素的值

代码例子:

// 使用 new 指定数组大小后进行初始化
int[] number = new int[5];
number[0] = 1;
number[1] = 2;
number[2] = 3;
number[3] = 4;
number[4] = 5;

// 使用 new 指定数组元素的值
int[] number = new int[] { 1, 2, 3, 4, 5 };   //不指定数组长度

// 直接指定数组元素的值
int[] number = { 1, 2, 3, 4, 5 };

易错点:
int[] number = new int[5] { 1, 2, 3, 4, 5 };  //注意,不能用这种方式初始化数组 ,语法错误

2. 二维数组

二维数组的定义

二维数组可当成两个一维数组,与一维数组的定义类似,二维数组也有两种声明方式:

数组元素类型 数组名字[][];

数组元素类型[][] 数组名字;  //推荐使用

二维数组初始化方法与一维数组类似

来看代码:

    public static void main(String[] args){

        int[][] a = { {1,2,3},{4,5,6} };   //直接给二维数组赋值
        int[][] a1= new int[][]{ {1,2,3}, {4,5,6} }; //使用构造函数初始化二维数组

        //分别给第一行和第二行的一维数组赋值
        int[][] a= new int[2][3];
        a[0] = new int[]{1,2,3};
        a[1] = new int[]{4,5,6};
    }

二维数组的两个下标,左索引决定行,由索引决定列。

 二维数组的内存分配: 以 int[][] a = new int[2][3]; 为例

 3. 数组的使用

数组的常用操作:遍历、排序、查询、复制等,下面以几个经典例子来进行说明。

1. 冒泡排序

算法思想:数组内的元素两两比较,将最大的元素放到最后(或最前)

    public static void main(String[] args){
        int arr[] = {88,1,9,22,99,6,100,6,35};
        for(int i=0;i < arr.length-1;i++) {//外层循环控制排序趟数
            for(int j=0; j< arr.length-i-1;j++) {
                //内层循环控制每一趟排序多少次
                // 把小的值交换到前面
                if (arr[j]>arr[j+1]) {
                    int temp = arr[j];
                    arr[j] = arr[j+1];
                    arr[j+1] = temp;
                }
            }
            System.out.print("第"+(i+1)+"次排序结果:");
            //列举每次排序的数据
            for(int a=0;a<arr.length;a++) {
                System.out.print(arr[a] + "\t");
            }
            System.out.println("");
        }
        System.out.println("最终排序结果:");
        for(int a = 0; a < arr.length;a++) {
            System.out.println(arr[a] + "\t");
        }

    }

结果:
第1次排序结果:1	9	22	88	6	99	6	35	100	
第2次排序结果:1	9	22	6	88	6	35	99	100	
第3次排序结果:1	9	6	22	6	35	88	99	100	
第4次排序结果:1	6	9	6	22	35	88	99	100	
第5次排序结果:1	6	6	9	22	35	88	99	100	
第6次排序结果:1	6	6	9	22	35	88	99	100	
第7次排序结果:1	6	6	9	22	35	88	99	100	
第8次排序结果:1	6	6	9	22	35	88	99	100	
最终排序结果:
1	
6	
6	
9	
22	
35	
88	
99	
100	

2. 选择排序

算法思想:将指定排序位置的元素与其他位置元素分别比较,找出最大的(或最小的)放到最后(或最前)

    public static void main(String[] args) {
        int[] arr = new int[]{88,1,9,22,99,6,100,6,35};
        // int index;
        for (int i =0; i<arr.length-1; i++) {
            int index = 0;
            for (int j =1; j<=arr.length-i-1; j++) {
                if (arr[j]>=arr[index]) {          //找出数组中最大的一个数
                    index = j;                     //指针指向最大的元素
                }
            }
            int tmp = arr[arr.length-i-1];
            arr[arr.length-i-1] = arr[index];      //将最大的数放到最后
            arr[index] = tmp;
        }
        System.out.println("选择排序的结果:");
        for (int a:arr) {                          //foreach遍历
            System.out.println(a);
        }
    }


选择排序的结果:
1
6
6
9
22
35
88
99
100

3. 反转排序

算法思想:将数组两边的元素进行替换。

    public static void main(String[] args) {
        int[] arr = new int[]{88,1,9,22,99,6,100,6,35};
        System.out.println("初始数组:");
        for (int a:arr) {
            System.out.print(a + "\t");
        }
        System.out.println("");
        for (int i =0; i<arr.length/2; i++) {
            int tmp = arr[i];
            arr[i] = arr[arr.length-i-1];    //反序交换元素值
            arr[arr.length-i-1] = tmp;
        }


        System.out.println("反转排序的结果:");
        for (int a:arr) {
            System.out.print(a + "\t");
        }
    }

结果:
初始数组:
88	1	9	22	99	6	100	6	35	
反转排序的结果:
35	6	100	6	99	22	9	1	88

三种排序方式的比较:

1)冒泡排序

时间复杂度:O(n^2)

  • 最好情况:已经排完序,为O(n)
  • 最坏情况:逆序排列,为O(n^2)
  • 平均情况:O(n^2)

空间复杂度:O(1)

  • 冒泡排序在原地排序,只需要常数级别的辅助空间,因此空间复杂度为O(1)。

内存占用情况:

  • 冒泡排序也是一种比较消耗内存的算法,因为它需要在排序过程中不断交换相邻的元素,每次交换都需要使用一个临时变量来存储数据,因此它的内存占用情况较高。

2)选择排序

时间复杂度:O(n^2)

  • 最好情况和最坏情况时间复杂度都为O(n^2)
  • 平均情况:O(n^2)

空间复杂度:O(1)

  • 选择排序也是一种原地排序的算法,只需要常数级别的辅助空间,因此空间复杂度为O(1)。

内存占用情况:

  • 相对于冒泡排序,选择排序的内存占用情况要略低一些,因为它只需要选择最小的元素,并将其与第一个元素进行交换,而不需要像冒泡排序一样不断交换相邻的元素,因此它的内存占用情况较低。

3)反序排序

时间复杂度:O(n)

  • 反序排序只需要对已经排完序的数据进行一次翻转,因此时间复杂度为O(n)。

空间复杂度:O(1)

  • 反序排序也是一种原地排序的算法,只需要常数级别的辅助空间,因此空间复杂度为O(1)。

内存占用情况:

  • 反序排序在排序过程中并没有进行任何的比较和交换操作,因此它的内存占用情况非常低。

总的来说,这3种排序方法都是原地排序算法,冒泡排序和选择排序时间复杂度均为O(n^2),空间复杂度均为O(1),内存占用情况较高;而反序排序时间复杂度为O(n),空间复杂度为O(1),内存占用情况非常低。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值