首页 > 编程语言 >Java 数组

Java 数组

时间:2024-09-27 10:52:30浏览次数:3  
标签:Java String int 元素 Arrays 数组 new

目录

1 基本概念

2 数组的定义 

2.1 声明数组

2.2 初始化数组

2.2.1 动态初始化 

2.2.2 静态初始化

3 数组常用方法

3.1 获取数组长度

3.2 数组排序

3.3 数组复制

3.4 数组填充

3.5 数组转换为字符串

3.6 数组比较

3.7 查找数组中的元素

3.8 数组转列表

4 多维数组

4.1 二维数组

4.1.1 声明和创建

4.1.2 初始化

4.1.2.1 动态初始化

4.1.2.2 静态初始化

4.1.3 访问和修改元素

4.2 不规则数组

4.2.1 声明和创建

4.2.2 初始化

4.2.3 访问和修改元素 

5 数组在内存中的存储 

5.1 栈(Stack)与堆(Heap)

5.2 数组在内存中的存储

5.3 内存布局示例


在Java中,数组是一种可以存储固定大小的相同类型元素的数据结构。数组中的每个元素都可以通过索引(一个非负整数)来访问,这些索引从0开始,直到length-1

1 基本概念

数组是一种线性数据结构,它能够存储固定数量的相同类型的元素。在Java中,数组具有以下特性:

  • 固定大小:一旦创建,数组的长度(即它可以容纳的元素数量)是固定的。如果你需要一个可以动态改变大小的数据结构,可能需要考虑使用ArrayList或其他集合类。

  • 相同类型:数组中的所有元素必须是相同的数据类型。这个类型是在声明数组时指定的,并且不能更改。

  • 索引访问:数组中的每个元素都可以通过其索引来访问,索引从0开始。例如,在一个有5个元素的数组中,第一个元素位于索引0,最后一个元素位于索引4。

2 数组的定义 

在Java中,定义数组通常涉及两个步骤:声明和初始化。下面详细说明这两个步骤:

2.1 声明数组

声明数组意味着告诉编译器你将要使用的数组变量的名称及其所包含的数据类型。语法如下:

dataType[] arrayName;
// 或
dataType arrayName[];

这里 dataType 是数组元素的数据类型,而 arrayName 是数组变量的名字。例子如下:

int[] scores; // 声明了一个整型数组
String[] names; // 声明了一个字符串数组

2.2 初始化数组

初始化数组意味着为数组分配内存并可能设置初始值。这可以通过两种方式完成:

  • 动态初始化:使用 new 关键字创建数组,并指定数组的大小。
  • 静态初始化:直接用一组值来初始化数组。
2.2.1 动态初始化 

当你知道数组的大小但还没有具体的值时,可以使用 new 来创建数组。

arrayName = new dataType[arraySize];

示例代码:

scores = new int[5]; // 创建一个能存放5个整数的数组
names = new String[3]; // 创建一个能存放3个字符串的数组

你动态创建一个数组时,数组的元素会被自动初始化为该类型默认的初始值。这些默认值取决于数组元素的数据类型。以下是各种数据类型的默认值:

  • 数值类型

    • byte:0
    • short:0
    • int:0
    • long:0L
    • float:0.0f
    • double:0.0d
  • 布尔类型

    • booleanfalse
  • 引用类型(包括对象和数组):

    • null(表示没有引用任何对象)

示例代码:

public class ArrayInitializationExample {
    public static void main(String[] args) {
        // 数值类型数组
        int[] intArray = new int[5];
        System.out.println("int array default values: " + java.util.Arrays.toString(intArray));

        long[] longArray = new long[5];
        System.out.println("long array default values: " + java.util.Arrays.toString(longArray));

        float[] floatArray = new float[5];
        System.out.println("float array default values: " + java.util.Arrays.toString(floatArray));

        double[] doubleArray = new double[5];
        System.out.println("double array default values: " + java.util.Arrays.toString(doubleArray));

        // 布尔类型数组
        boolean[] booleanArray = new boolean[5];
        System.out.println("boolean array default values: " + java.util.Arrays.toString(booleanArray));

        // 引用类型数组
        String[] stringArray = new String[5];
        System.out.println("String array default values: " + java.util.Arrays.toString(stringArray));
    }
}

输出结果:

int array default values: [0, 0, 0, 0, 0]
long array default values: [0, 0, 0, 0, 0]
float array default values: [0.0, 0.0, 0.0, 0.0, 0.0]
double array default values: [0.0, 0.0, 0.0, 0.0, 0.0]
boolean array default values: [false, false, false, false, false]
String array default values: [null, null, null, null, null]

在这个例子中,你可以看到每种类型的数组都被初始化为其默认值。对于基本类型的数组,每个元素被初始化为零或false;而对于引用类型的数组,每个元素被初始化为null。 

2.2.2 静态初始化

如果在创建数组时已经有了具体的值,可以直接用这些值来初始化数组。

dataType[] arrayName = {value0, value1, ..., valueN};

示例代码:

int[] scores = {98, 92, 76, 88, 95}; // 初始化一个整型数组
String[] names = {"Alice", "Bob", "Charlie"}; // 初始化一个字符串数组

在这个例子中,数组的大小由提供的值的数量自动确定,不需要显式地指定。

示例代码:下面是完整的示例代码,展示了如何声明、创建和初始化数组:

public class ArrayExample {
    public static void main(String[] args) {
        // 声明数组
        int[] numbers;
        
        // 使用new关键字创建数组
        numbers = new int[5];
        
        // 打印数组长度
        System.out.println("数组长度: " + numbers.length);
        
        // 直接初始化数组
        int[] values = {1, 2, 3, 4, 5};
        
        // 遍历并打印数组元素
        for (int i = 0; i < values.length; i++) {
            System.out.println("Element at index " + i + ": " + values[i]);
        }
    }
}

3 数组常用方法

3.1 获取数组长度

  • 方法arrayName.length
  • 说明: 这不是方法调用,而是访问数组的length属性。它返回数组中元素的数量。
int[] numbers = {1, 2, 3, 4, 5};
int length = numbers.length; // length 将是 5

3.2 数组排序

  • 方法Arrays.sort(array)
  • 说明: 使用java.util.Arrays类的sort方法对数组进行排序。
import java.util.Arrays;

int[] numbers = {5, 3, 2, 4, 1};
Arrays.sort(numbers); // 排序后的数组: [1, 2, 3, 4, 5]

3.3 数组复制

  • 方法Arrays.copyOf(array, newLength) 或 System.arraycopy(src, srcPos, dest, destPos, length)
  • 说明Arrays.copyOf用于创建一个新数组,并将原数组的内容复制到新数组中。System.arraycopy用于直接复制数组的一部分或全部内容到另一个数组。
import java.util.Arrays;

int[] original = {1, 2, 3, 4, 5};
int[] copy = Arrays.copyOf(original, original.length); // 创建一个完全相同的副本

// 或者使用 System.arraycopy
int[] anotherCopy = new int[original.length];
// 参数:源数组,源数组中起始位置,目标数组,目标数组起始位置,要复制的数组元素数量
System.arraycopy(original, 0, anotherCopy, 0, original.length);

3.4 数组填充

  • 方法Arrays.fill(array, value) 或 Arrays.fill(array, fromIndex, toIndex, value)
  • 说明: 使用指定值填充整个数组或数组的一部分。
import java.util.Arrays;

int[] numbers = new int[5];
Arrays.fill(numbers, 7); // 所有元素都被设置为 7: [7, 7, 7, 7, 7]

Arrays.fill(numbers, 1, 4, 9); // 从索引1到3(不包括4)的元素被设置为 9: [7, 9, 9, 9, 7]

3.5 数组转换为字符串

  • 方法Arrays.toString(array)
  • 说明: 将数组转换成一个包含所有元素的字符串表示形式,方便打印输出。
import java.util.Arrays;

int[] numbers = {1, 2, 3, 4, 5};
String str = Arrays.toString(numbers); // 结果: "[1, 2, 3, 4, 5]"
System.out.println(str);

3.6 数组比较

  • 方法Arrays.equals(array1, array2)
  • 说明: 比较两个数组是否相等(即它们的长度相同且对应位置的元素都相等)。
import java.util.Arrays;

int[] a1 = {1, 2, 3};
int[] a2 = {1, 2, 3};
boolean isEqual = Arrays.equals(a1, a2); // 返回 true

3.7 查找数组中的元素

  • 方法Arrays.binarySearch(array, key) 或 Arrays.binarySearch(array, fromIndex, toIndex, key)
  • 说明: 对已排序的数组执行二分查找。如果找到,则返回元素的索引;否则返回负数(插入点的反码)。
import java.util.Arrays;

int[] numbers = {1, 2, 3, 4, 5};
int index = Arrays.binarySearch(numbers, 3); // 返回 2

3.8 数组转列表

  • 方法Arrays.asList(array)
  • 说明: 将数组转换为列表。注意,对于原始类型数组,这不会工作,但对于对象类型的数组是有效的。
  • 注意:当你使用 Arrays.asList(strings) 将数组转换为列表时,实际上得到的是一个固定大小的列表。这个列表是 Arrays 类内部实现的一个私有静态类,它直接包装了原始数组,因此不支持添加或删除元素的操作。操作时会抛出 UnsupportedOperationException 异常。
import java.util.Arrays;
import java.util.List;

String[] strings = {"a", "b", "c"};
List<String> list = Arrays.asList(strings); // 转换为 List

 以上转换的列表list是不能添加删除元素的,要解决这个可以使用一下方法之一:

方法1:使用 ArrayList 构造函数

你可以将 Arrays.asList() 返回的列表传递给 ArrayList 的构造函数来创建一个新的可修改的列表。

String[] strings = {"a", "b", "c"};
List<String> list = new ArrayList<>(Arrays.asList(strings)); // 转换为可变 List
System.out.println(list);
list.add("d");
System.out.println(list);

方法2:使用 Collections.addAll()

你也可以先创建一个空的 ArrayList,然后使用 Collections.addAll() 方法来添加数组中的所有元素。

String[] strings = {"a", "b", "c"};
List<String> list = new ArrayList<>(); // 创建一个新的可变 List
Collections.addAll(list, strings); // 添加数组中的所有元素
System.out.println(list);
list.add("d");
System.out.println(list);

4 多维数组

多维数组是数组的一种扩展形式,它允许你在多个维度上组织数据。在Java中,最常见的是二维数组(也称为矩阵),但也可以有三维或更多维度的数组。下面是对多维数组的详细解释:

4.1 二维数组

4.1.1 声明和创建

二维数组可以看作是“数组的数组”。每个元素本身也是一个数组。

声明:

dataType[][] arrayName;

创建:

arrayName = new dataType[rows][columns];

或者同时声明和创建:

arrayName = new dataType[rows][columns];
4.1.2 初始化
4.1.2.1 动态初始化
int[][] matrix = new int[3][3];
matrix[0][0] = 1;
matrix[0][1] = 2;
matrix[0][2] = 3;
matrix[1][0] = 4;
matrix[1][1] = 5;
matrix[1][2] = 6;
matrix[2][0] = 7;
matrix[2][1] = 8;
matrix[2][2] = 9;
4.1.2.2 静态初始化
int[][] matrix = {
    {1, 2, 3},
    {4, 5, 6},
    {7, 8, 9}
};
4.1.3 访问和修改元素

可以通过双重索引访问和修改二维数组中的元素。

int value = matrix[1][2]; // 获取第二行第三列的值 (6)
matrix[1][2] = 60; // 修改第二行第三列的值为 60

可以使用嵌套的 for 循环来遍历二维数组。

for (int i = 0; i < matrix.length; i++) {
    for (int j = 0; j < matrix[i].length; j++) {
        System.out.print(matrix[i][j] + " ");
    }
    System.out.println();
}

4.2 不规则数组

不规则数组是指每一行的长度可以不同的二维数组。这种数组在实际应用中非常常见,例如表示树结构或稀疏矩阵。

4.2.1 声明和创建
dataType[][] arrayName;
arrayName = new dataType[rows][];
4.2.2 初始化

每一行可以有不同的长度。

String[][] jaggedArray = new String[3][];
jaggedArray[0] = new String[2];
jaggedArray[1] = new String[3];
jaggedArray[2] = new String[1];

jaggedArray[0][0] = "A";
jaggedArray[0][1] = "B";
jaggedArray[1][0] = "C";
jaggedArray[1][1] = "D";
jaggedArray[1][2] = "E";
jaggedArray[2][0] = "F";
4.2.3 访问和修改元素 

可以通过双重索引访问和修改不规则数组中的元素。

String value = jaggedArray[1][2]; // 获取第二行第三列的值 ("E")
jaggedArray[1][2] = "G"; // 修改第二行第三列的值为 "G"

可以使用嵌套的 for 循环来遍历不规则数组。 

for (int i = 0; i < jaggedArray.length; i++) {
    for (int j = 0; j < jaggedArray[i].length; j++) {
        System.out.print(jaggedArray[i][j] + " ");
    }
    System.out.println();
}

5 数组在内存中的存储 

数组是一种基础的数据结构,用于在内存中连续存储相同类型的数据。了解数组在内存中的存储方式对于优化程序性能、理解垃圾回收机制以及进行内存管理等方面都非常重要。下面是对Java数组在内存中的存储方式的详细分析:

5.1 栈(Stack)与堆(Heap)

  • 栈(Stack):

    • 栈是用于存储方法调用和局部变量的地方。
    • 每当一个方法被调用时,一个新的栈帧(stack frame)被创建,其中包含该方法的局部变量、方法参数和返回地址。
    • 栈内存的分配和释放非常快,因为它遵循后进先出(LIFO)的原则。
    • 栈内存是线程私有的,每个线程有自己的栈。
  • 堆(Heap):

    • 堆是所有线程共享的内存区域,用于存储对象实例和数组。
    • 使用new关键字创建的对象和数组都存储在堆中。
    • 堆内存的分配和释放较慢,因为需要进行垃圾回收(Garbage Collection, GC)来管理不再使用的对象。
    • 堆内存的大小通常比栈内存大得多,并且可以根据应用程序的需求动态扩展。

5.2 数组在内存中的存储

数组引用:当你在代码中声明一个数组变量时,实际上是在栈上创建了一个引用(指针),指向堆上的实际数组数据。

int[] numbers;

这里,numbers 是一个栈上的引用,它还没有指向任何具体的数组对象。

数组对象:当你使用 new 关键字创建数组时,会在堆上分配一块连续的内存空间来存储数组的数据。

numbers = new int[5];

这里,new int[5] 在堆上创建了一个包含5个整数的数组,并且 numbers 引用指向了这个数组的起始位置。

数组元素:

  • 对于原始类型(如 int, char, boolean 等),数组中的每个元素直接存储在堆中,每个元素占据固定的内存空间。

  • 例如,int 类型的每个元素占用4个字节。

  • 对于引用类型(如 String, Object 等),数组中的每个元素是一个引用,指向堆中的实际对象。

String[] names = new String[3];
names[0] = "Alice";
names[1] = "Bob";

 这里,names 数组中的每个元素是一个指向 String 对象的引用。"Alice""Bob" 都是独立的对象,分别存储在堆中。

5.3 内存布局示例

假设我们有以下代码:

public class ArrayMemoryExample {
    public static void main(String[] args) {
        String[] names = new String[3]; // 创建一个字符串数组
        names[0] = "Alice";
        names[1] = "Bob";
    }
}

内存布局详解:

  • 栈内存 (Stack):

    • 在 main 方法的栈帧中,有一个局部变量 names,它是一个引用,指向堆中的 String 数组。
    • names 引用存储在栈内存中。
  • 堆内存 (Heap):

    • 当执行 String[] names = new String[3]; 时,在堆内存中分配了一块空间来存储一个 String 数组。这个数组有3个元素,每个元素都是一个 String 引用。
    • 每个 String 引用(names[0]names[1]names[2])也存储在堆内存中。
    • 当执行 names[0] = "Alice"; 和 names[1] = "Bob"; 时,堆内存中会创建两个 String 对象 "Alice" 和 "Bob",并且 names[0] 和 names[1] 分别指向这两个 String 对象。

图解: 为了更直观地理解,可以画一个简单的图示。

+-----------------+
|  栈 (Stack)     |
| +-------------+ |
| |  names      | |  <--- 指向堆中的 String[] 数组
| +-------------+ |
+-----------------+

+-----------------+
|  堆 (Heap)      |
| +-------------+ |
| |  String[]   | |  <--- 包含 3 个 String 引用
| |  [0]        | |  <--- 指向 "Alice"
| |  [1]        | |  <--- 指向 "Bob"
| |  [2]        | |  <--- null
| +-------------+ |
| +-------------+ |
| |  "Alice"    | |  <--- String 对象
| +-------------+ |
| +-------------+ |
| |  "Bob"      | |  <--- String 对象
| +-------------+ |
+-----------------+

总结:

  • names 是一个引用,存储在栈内存中。
  • names 指向的 String 数组存储在堆内存中。
  • String 数组中的每个元素(即 String 引用)也存储在堆内存中。
  • 实际的 String 对象(如 "Alice" 和 "Bob")存储在堆内存中,并由 String 数组中的引用指向。

标签:Java,String,int,元素,Arrays,数组,new
From: https://blog.csdn.net/weixin_47363690/article/details/142584841

相关文章

  • Java面试-数据库篇-优化
    如何定位慢查询面试话术HR:MySQL中,如何定位慢查?我:        我们当时做压测的时候有的接口非常的慢,接口的响应时间超过了2秒以上,因为我们当时的系统部署了运维的监控系统skywalking,在展示的报表中可以看到是哪一个接口比较慢,并且可以分析这个接口哪部分比较慢,这里......
  • JavaScript null和0和undefined的比较
    null和0和undefined的比较alert(null>0); //(1)falsealert(null==0);//(2)falsealert(null>=0);//(3)true注意:这是因为相等性检查 == 和普通比较符 ><>=<= 的代码逻辑是相互独立的。进行值的比较时,null 会被转化为数字,因此它被转化为了 0。这就是为......
  • 三大硬核方式揭秘:Java如何与底层硬件和工业设备轻松通信!
    大家好,我是V哥,程序员聊天真是三句不到离不开技术啊,这不前两天跟一个哥们吃饭,他是我好多年前的学员了,一直保持着联系,现在都李总了,在做工业互联网相关的项目,真是只要Java学得好,能干一辈子,卷死的是那些半吊子。感谢李总给我分享了工业互联网项目的事情,收获很多,今天的内容来聊一聊......
  • javascript 匿名函数之立即执行
    函数分为具名函数和匿名函数,具名函数需要先声明在进行调用,而匿名函数是完全没有值。例如:我们设置点击事件中的function就是匿名函数document.addEventListener('click',function(){})我们可以设置匿名函数立即执行。好处是一方面可以防止变量污染,另外一方面,......
  • 获取某宝商品详情:Java爬虫数据的艺术
    某宝商品详情的重要性商品详情包括商品标题、价格、销量、评价、图片等信息,这些信息对于市场分析、客户洞察、内容监控等多种业务场景至关重要。Java爬虫基础Java爬虫是指使用Java语言编写的程序,用于从互联网上的网页中提取数据。Java爬虫通常使用HTTP客户端库(如HttpClient、OkHttp......
  • java计算机毕业设计公益捐赠管理系统(开题+程序+论文)
    本系统(程序+源码)带文档lw万字以上 文末可获取一份本项目的java源码和数据库参考。系统程序文件列表开题报告内容研究背景随着社会的快速发展与公众慈善意识的日益增强,公益捐赠活动已成为促进社会和谐、资源循环利用的重要途径。然而,传统的公益捐赠模式往往面临信息不对称......
  • java计算机毕业设计安徽旅游网(开题+程序+论文)
    本系统(程序+源码)带文档lw万字以上 文末可获取一份本项目的java源码和数据库参考。系统程序文件列表开题报告内容研究背景随着旅游业的蓬勃发展,数字化与智能化已成为提升旅游体验、优化资源配置的关键路径。安徽,作为中国历史悠久、文化底蕴深厚且自然风光秀丽的省份,其旅游......
  • java计算机毕业设计高校心理咨询系统(开题+程序+论文)
    本系统(程序+源码)带文档lw万字以上 文末可获取一份本项目的java源码和数据库参考。系统程序文件列表开题报告内容研究背景:在当今快节奏的校园生活中,大学生面临着学业压力、人际关系、职业规划等多重挑战,心理健康问题日益凸显,成为影响学生全面发展的重要因素。传统的高校心......
  • java计算机毕业设计大学生社团管理系统(开题+程序+论文)
    本系统(程序+源码)带文档lw万字以上 文末可获取一份本项目的java源码和数据库参考。系统程序文件列表开题报告内容研究背景随着高等教育的蓬勃发展,大学生社团作为校园文化的重要组成部分,日益成为促进学生综合素质提升、兴趣爱好培养及团队协作能力增强的关键平台。然而,传统......
  • 如何使用JAVA获取淘宝商品详情?
    在电子商务的世界里,淘宝作为一个庞大的在线购物平台,拥有丰富的商品信息。对于开发者来说,能够获取淘宝商品的详细信息是一项非常有用的技能。本文将介绍如何使用Java编写爬虫程序,获取淘宝商品的详细信息。淘宝商品详情的重要性淘宝商品详情包括商品标题、价格、销量、评价、图片......