0%

Java数组

数组的声明和创建

数组的基本概念

数组是 Java 中一种复合数据类型,用于存储多个相同类型的值。它是一个固定大小的容器,元素通过下标(索引)访问,下标从 0 开始。数组的优势在于高效的随机访问(O(1) 时间复杂度),但大小固定,无法动态扩展(需用 ArrayList 等集合替代)。
数组的元素可以是基本类型(如 int、double)或引用类型(如 String、对象)。数组本身是引用类型,存储在堆内存中。

数组的声明

声明数组时,指定元素类型和数组名,但不分配内存。语法:

  • 类型[] 数组名;
  • 类型 数组名[];
1
2
3
int[] scores;     // 声明整数数组
String[] names; // 声明字符串数组
double[] prices; // 声明双精度数组

注意:声明后,数组变量为 null(未初始化)。直接使用会抛 NullPointerException。

数组的创建(分配内存)

创建数组时,使用 new 关键字分配内存,并指定长度。语法:

  • 数组名 = new 类型[长度];
    1
    2
    scores = new int[5];  // 创建长度为5的int数组,默认元素为0
    names = new String[3]; // 创建长度为3的String数组,默认元素为null
    结合声明和创建:
    1
    int[] ages = new int[4];
    需要注意的细节:长度必须是正整数或者0(空数组),负数或非整型会编译错误,创建后,基本元素默认会进行初始化,比如:int[] ages = new int[4]; 数组中的4个值均为0.

简单数组的创建

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
public class ArrayDeclareCreate {
public static void main(String[] args) {
// 声明并创建
char[] letters = new char[4];

// 访问和赋值
letters[0] = 'A';
letters[1] = 'B';
letters[2] = 'C';
letters[3] = 'D';

// 输出
System.out.println("数组长度:" + letters.length); // 4
System.out.println("第一个元素:" + letters[0]); // A
}
}

常见错误的分析

  • 未创建直接使用:如:int[] arr; arr[0]=1;会抛NullPointerException
  • 长度为变量:允许,但是变量必须初始化,如:int size = 5; int[] array = new int[size];
  • 多维数组声明:声明如int[][] matrix;

需要注意的是:数组是引用类型,多个变量可引用同一数组(如 int[] a = new int[3]; int[] b = a; 修改 a 影响 b)。

三种初始化及内存分析

三种初始化的基本概念

初始化是为数组元素赋值。Java 支持三种方式:

  • 动态初始化:创建后逐个赋值。
  • 静态初始化:创建时直接指定元素值,长度自动推导。
  • 默认初始化:创建时不赋值,使用默认值。

动态初始化

先创建数组,再通过循环或单个赋值初始化。

1
2
3
4
int[] nums = new int[3];
nums[0] = 10;
nums[1] = 20;
nums[2] = 30;

静态初始化

语法:类型[] 数组名 = new 类型[] {值1, 值2, ...}; 或简写 类型[] 数组名 = {值1, 值2, ...};(仅限声明时)。

1
2
3
String[] fruits = new String[] {"a", "b", "c", "d"};
// 或者
double[] temps = {1.1, 2.3, 5.6, 2.9};

细节:元素类型必须匹配。简写形式不能用于已声明变量,如 String[] fruits; fruits = {“A”, “B”}; 会编译错误,必须用 new。

默认初始化

  • 创建时自动:基本类型为 0/false/‘’,引用为 null。
  • 示例:new boolean[2] 默认 {false, false}。

内存分析

Java内存分为栈(Stack)和堆(Heap):

  • 栈:存储局部变量、方法调用、数组变量在栈中
  • 堆:存储数组实体元素
    1
    2
    3
    4
    int[] arr = new int[3];  // 栈:arr 引用;堆:分配 int[3] 空间,默认 0,0,0
    arr[0] = 1; // 修改堆中元素
    int[] arr2 = arr; // 栈:arr2 指向同一堆数组
    arr2[1] = 2; // 修改影响 arr
    图解(文字描述):
    栈:arr -> 地址0x123
    堆:0x123 [0:1, 1:2, 2:0]

垃圾回收:当无引用时,堆数组被 GC 回收。

结合三种初始化

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
public class ArrayInitMemory {
public static void main(String[] args) {
// 默认初始化
int[] defaults = new int[2];
System.out.println(defaults[0]); // 0

// 动态
defaults[0] = 100;
defaults[1] = 200;

// 静态
char[] chars = {'X', 'Y', 'Z'};

// 内存:defaults 和 chars 在堆,不同地址
}
}

常见错误避免

  • 静态初始化类型不匹配:如 int[] = {“1”}; 错误。
  • 简写形式误用:声明后赋值必须 new。
  • 内存泄漏:过多大数组未释放,导致 OutOfMemoryError。