在Java里,数组是一种容器对象,用来存放固定数量的同类型元素。很多初学者在写循环或判断边界时,第一个遇到的问题就是:怎么知道这个数组里到底有几个元素?答案其实很简单,Java为每一个数组对象都内置了一个叫作length的实例属性,它不是方法,而是一个final修饰的整型变量,直接通过数组引用去点取即可。

之所以容易混淆,是因为String类也有表示长度的概念,但String用的是length()方法,而数组用的是length属性。编译器在语法层面就做了区分,如果对一个数组调用length(),会直接报“无法对数组应用方法调用”的错误。从底层实现看,JVM在创建数组时会在对象头之外分配空间记录元素个数,这个数值就是length,并且在数组生命周期内不允许修改。
一、一维数组的length基本用法
对于最常见的一维数组,获取长度的方式非常直观。无论数组里放的是int、double这类基本类型,还是Object及其子类的引用,语法完全一致。下面的例子展示了如何声明数组、赋予初始值并读取长度:
public class ArrayLengthDemo {
public static void main(String[] args) {
// 基本类型数组
int[] nums = {10, 20, 30, 40};
System.out.println("nums数组长度: " + nums.length);
// 对象类型数组
String[] names = new String[5];
System.out.println("names数组长度: " + names.length);
// 遍历时使用length控制边界
for (int i = 0; i < nums.length; i++) {
System.out.println("索引 " + i + " 的值是 " + nums[i]);
}
}
}
上面代码中,nums在声明时直接给了四个元素,因此length返回4;names通过new String[5]指定了容量,length返回5,即使里面还没有放任何实际字符串对象,长度也已经是5。把nums.length放进循环条件,是保证不越界的最安全写法。
需要注意,length是数组对象自身的属性,不是继承自某个父类的可变字段。试图对length赋值,例如nums.length = 10,会在编译期就被拒绝,因为final变量不允许重新绑定。这种设计从语言层面杜绝了运行时擅自扩容带来的安全隐患。
二、多维数组的length陷阱
Java并没有真正的多维数组,只有数组的数组。以二维数组为例,它其实是一个一维数组,其中每个元素又是一个一维数组的引用。因此,二维数组变量的length只表示“外层有多少个内层数组”,而不是总的元素个数。
public class MultiArrayLength {
public static void main(String[] args) {
int[][] matrix = {
{1, 2, 3},
{4, 5},
{6, 7, 8, 9}
};
// 外层长度,即有几行
System.out.println("行数: " + matrix.length);
// 每一行的长度需要单独取
for (int i = 0; i < matrix.length; i++) {
System.out.println("第 " + i + " 行长度: " + matrix[i].length);
}
}
}
运行后会发现,matrix.length是3,代表有三行;而matrix[0].length是3,matrix[1].length是2,matrix[2].length是4。这种不规则的二维数组在Java里完全合法,也正因如此,不能想当然地用matrix.length * matrix[0].length去算总元素量,必须逐行累加。
如果定义了一个规则矩阵,比如int[][] grid = new int[3][4],那么grid.length是3,grid[0].length是4,此时总元素数才是两者相乘。但在实际代码中,只要涉及多维数组遍历,最稳妥的写法依旧是外层用grid.length,内层用grid[i].length,不依赖任何先验假设。
三、空数组与null引用的区别
另一个常见误区是把长度为0的数组和null引用混为一谈。长度为0的数组是一个真实存在的数组对象,只是里面没有元素,它的length返回0;而null表示根本没有指向任何数组对象,此时访问length会抛出NullPointerException。
public class NullVsEmpty {
public static void main(String[] args) {
int[] empty = new int[0];
System.out.println("空数组长度: " + empty.length); // 输出0
int[] nullArr = null;
// 下面这行若放开注释会抛NullPointerException
// System.out.println(nullArr.length);
if (nullArr != null) {
System.out.println(nullArr.length);
} else {
System.out.println("数组引用为null,无法获取长度");
}
}
}
在方法返回值或字段初始化时,推荐返回空数组而不是null,这样调用方可以统一用arr.length来判断并处理,不必每次都做空指针检查。例如返回一个过滤后的结果集,即使没有匹配项,也返回new String[0],能让下游代码更简洁。
总结来说,Java数组长度的获取完全依赖length属性,它简单、高效且线程安全,因为数组长度不可变。只要分清属性与方法、一维与多维、空数组与null这三组概念,就能在各类业务代码里稳妥地使用它。