随堂笔记之Java数组

此内容源自

B站狂神说Java基础

的课后笔记与总结,用于复习和查看,因此写得比较简陋,不太适合萌新学习

数组的定义

相同类型数据的有序集合
数组是对象,数组元素是成员变量(实例变量),因此可以自动初始化,有默认值

数组的声明创建

数据类型[] 数组名;  // 推荐写法
数据类型 数组名[];  // 也可以这样写(但不推荐)

int[] numbers;  // 声明一个存储整数的数组
double[] scores;  // 声明一个存储浮点数的数组
String[] names;  // 声明一个存储字符串的数组

numbers = new int[5];  // 创建一个长度为5的 int 数组

int[] numbers = new int[5];  // 默认初始化为 [0, 0, 0, 0, 0]

数组的三种初始化

  • 静态初始化
//定义时直接赋值,数组大小由元素个数确定
数据类型[] 数组名 = {元素1, 元素2, ...};
数据类型[] 数组名 = new 数据类型[]{元素1, 元素2, ...};

int[] arr1 = {1, 2, 3, 4, 5};  // 省略 new
int[] arr2 = new int[]{10, 20, 30};  // 带 new
String[] names = {"张三", "李四", "王五"};  // 字符串数组
  • 动态初始化
//只指定数组长度,元素默认初始化为 0(数值类型)/ false(boolean)/ null(引用类型)
数据类型[] 数组名 = new 数据类型[数组长度];

int[] arr = new int[5];  // 长度为 5,默认值全是 0
double[] scores = new double[3];  // 默认值 0.0
boolean[] flags = new boolean[4];  // 默认值 false
String[] strs = new String[2];  // 默认值 null
  • 默认初始化
    数组本身是对象,即使没有显式初始化,数组的元素也会有默认值。
    适用于动态初始化时的情况

内存分析

Java内存可以简单分为栈(Stack)、堆(Heap)、方法区(Method Area),它们的作用不同:


  • 存放方法的局部变量(基本类型变量和对象引用),每次方法调用时,都会创建一个新的“栈帧”,方法结束后自动销毁。
    特点:速度快,空间小,变量随方法执行完毕后自动释放

  • 存放对象和数组,所有new关键字创建的对象都会存放在堆里
    特点:堆中的对象不会自动销毁,靠垃圾回收(GC)回收
  • 方法区
    存放类的元信息(比如类名、方法、静态变量等)
    特点:存储所有类的信息,所有线程共享

通俗解释:

  • 栈就像是上菜的托盘,上菜(调用方法)时会放上新的托盘,吃完菜(方法结束)就把托盘收走。
  • 堆就像餐厅的桌子,顾客(对象)坐在那里,吃完饭(不再使用)后,清洁人员(GC)才会收拾。
  • 方法区就像菜单,存放了菜品信息(类信息和静态变量),所有人都可以查看。

数组的遍历

总结最常用两种:

  • 普通for循环(常用)
int[] numbers = {10, 20, 30, 40, 50};

for (int i = 0; i < numbers.length; i++) {
    System.out.println("索引 " + i + " 的值:" + numbers[i]);
}
  • 增强for循环(常用,但无法取下标)
int[] numbers = {10, 20, 30, 40, 50};

for (int num : numbers) {
    System.out.println("元素值:" + num);
}

二维数组

二维数组可以看作是“数组的数组”,即每个元素本身还是一个数组,常用于表示矩阵、表格或棋盘等结构

数据类型[][] 数组名;
数据类型 数组名[][];
数据类型[] 数组名[];

int[][] matrix;
double prices[][];
String[] names[];

//初始化
//静态初始化
int[][] matrix = {
    {1, 2, 3},
    {4, 5, 6},
    {7, 8, 9}
};

//动态初始化
int[][] matrix = new int[3][3];  // 创建 3x3 矩阵

// 赋值
matrix[0][0] = 1;
matrix[0][1] = 2;
matrix[0][2] = 3;

//锯齿状二维数组
int[][] jaggedArray = new int[3][];  // 只有行数,列数不定
jaggedArray[0] = new int[2];  // 第一行有2列
jaggedArray[1] = new int[3];  // 第二行有3列
jaggedArray[2] = new int[1];  // 第三行有1列

Arrays类

ctrl+F12打开structure面板

  • sort()用于对数组进行排序
    Arrays.sort(int[] array):对整数数组进行升序排序
    Arrays.sort(T[] array):对对象数组进行升序排序,默认使用 Comparable 接口
    Arrays.sort(int[] array, int fromIndex, int toIndex):对数组的指定部分进行排序
int[] arr = {3, 1, 4, 1, 5, 9};
Arrays.sort(arr);
System.out.println(Arrays.toString(arr));  // 输出:[1, 1, 3, 4, 5, 9]
  • binarySearch()用于在已经排序的数组中查找元素,返回该元素的索引,如果元素不存在,则返回负数
    Arrays.binarySearch(int[] array, int key):查找给定元素 key 在已排序数组中的索引
int[] arr = {1, 3, 4, 5, 9};
int index = Arrays.binarySearch(arr, 4);
System.out.println(index);  // 输出:2
  • equals()用于比较两个数组是否相等,比较的是数组的内容(即元素的值和顺序)
    Arrays.equals(int[] a, int[] b):比较两个整数数组是否相等
int[] arr1 = {1, 2, 3};
int[] arr2 = {1, 2, 3};
System.out.println(Arrays.equals(arr1, arr2));  // 输出:true
  • fill()用于将数组中的所有元素赋予指定的值
    Arrays.fill(int[] array, int value):用指定的值填充整个数组。
    Arrays.fill(int[] array, int fromIndex, int toIndex, int value):用指定的值填充数组的部分区域
int[] arr = new int[5];
Arrays.fill(arr, 10);
System.out.println(Arrays.toString(arr));  // 输出:[10, 10, 10, 10, 10]
  • copyOf()和copyOfRange()用于复制数组
    Arrays.copyOf(int[] original, int newLength):复制数组,并调整大小(可以增大或减小数组)
    Arrays.copyOfRange(int[] original, int from, int to):复制数组的指定范围
int[] arr = {1, 2, 3, 4};
int[] copyArr = Arrays.copyOf(arr, 6);
System.out.println(Arrays.toString(copyArr));  // 输出:[1, 2, 3, 4, 0, 0]
  • toString()用于返回数组的字符串表示
    Arrays.toString(int[] array):返回数组元素的字符串形式,格式为 [element1, element2, ..., elementN]
int[] arr = {1, 2, 3};
System.out.println(Arrays.toString(arr));  // 输出:[1, 2, 3]
  • stream()将数组转换为流(Stream),可以使用流的操作来处理数组中的元素
int[] arr = {1, 2, 3, 4, 5};
int sum = Arrays.stream(arr).sum();
System.out.println(sum);  // 输出:15

冒泡排序

工作原理(从下标0开始):

  1. 从数列的开始位置开始,依次比较相邻的元素。
  2. 如果当前元素比下一个元素大(升序排序),则交换这两个元素的位置。
  3. 一次遍历完成后,当前最大的元素已经排到数列的末尾。
  4. 忽略已排序好的最后一个元素,再次进行上述过程。
  5. 重复这个过程,直到整个数列有序
public class BubbleSort {
    public static void bubbleSort(int[] arr) {
        int n = arr.length;
        for (int i = 0; i < n - 1; i++) { // 外循环控制比较轮次
            for (int j = 0; j < n - 1 - i; j++) { // 内循环进行相邻元素比较
                if (arr[j] > arr[j + 1]) {
                    // 交换相邻元素
                    int temp = arr[j];
                    arr[j] = arr[j + 1];
                    arr[j + 1] = temp;
                }
            }
        }
    }

    public static void main(String[] args) {
        int[] arr = {5, 3, 8, 4, 2};
        bubbleSort(arr);
        // 输出排序后的数组
        for (int num : arr) {
            System.out.print(num + " ");
        }
    }
}

时间复杂度
最坏情况时间复杂度:O(n²),发生在输入数组是倒序时。
最好情况时间复杂度:O(n),当数组已经是有序的,且算法做了优化(比如在每一轮排序中没有发生交换时,可以提前终止,可以用一个flag来记录)。
平均时间复杂度:O(n²)

稀疏数组

//原数组
0  0  0  0  0  
0  3  0  0  0  
0  0  0  5  0  
0  0  0  0  0  
0  0  6  0  0  

//稀疏数组
行  列  值  
5   5   3  (稀疏数组头:总行数、总列数、非 0 元素个数)  
1   1   3  
2   3   5  
4   2   6  

posted @ 2025-03-25 09:53  _Tiffany  阅读(117)  评论(0)    收藏  举报