此内容源自
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开始):
- 从数列的开始位置开始,依次比较相邻的元素。
- 如果当前元素比下一个元素大(升序排序),则交换这两个元素的位置。
- 一次遍历完成后,当前最大的元素已经排到数列的末尾。
- 忽略已排序好的最后一个元素,再次进行上述过程。
- 重复这个过程,直到整个数列有序
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