一、数组的基本概念
1、什么是数组
指的是一种容器,可以同来存储同种数据类型的多个值。
但是数组容器在存储数据的时候,需要结合隐式转换考虑。
比如:
定义了一个int类型的数组。那么boolean。double类型的数据是不能存到这个数组中的,
但是byte类型,short类型,int类型的数据是可以存到这个数组里面的。
建议:
容器的类,和存储的数据类型保持一致。
举例:
整数1 2 3 4 56 就可以使用int类型的数组来存储。
小数1.1 1.2 1.3 1.4 就可以使用double类型的数组来存储。
字符串"aaa" "bbb" "ccc" 就可以使用String类型的数组来存储。
2、数组的创建
创建一个数组:
T[] 数组名; 比如 int[] array;
T 数组名[]; 比如 int array[] ;
3.数组的静态初始化
完整格式:
int[] arr = new int[]{11,22,33};
double[] arr = new double[]{1.1,1.2,1.3};
简化格式:
int[] array = {1,2,3,4,5};
double[] array = {1.1,1.2,1.3};
知道数组的内容,就可以静态初始化。
4.数组的动态初始化
//1.定义一个数组,存3个人的年龄,年龄未知 int[] agesArr = new int[3];
如果不知道数组的内容,那么就可以使用动态初始化。
如果对数组进行动态初始化,数组中的元素有默认值。不同的数据类型有不同的默认值,如果是简单类型,大多是默认值为0。float是0.0f,double是0.0,char是/u0000,boolean是false;引用类型比如字符串类型则是null。
二、一维数组的使用
1、数组元素的访问
数组在内存中是一段连续的空间,下标是从0开始的。
数组是一段连续的内存空间,因此支持随机访问,即通过下标访问快速访问数组中任意位置的元素。数组的下标从0开始,介于[0, N)之间不包含N,N为元素个数,不能越界,否则会报出下标越界异常。
2、数组的遍历
在Java中,对数组的遍历有两种方式:第一种是for,第二种是增强for(foreach)。
由于Java是面向对象的语言,在Java中,一切都是对象,比如数组。数组这个对象有它的属性,比如数组的长度等,基于这一点,我们可以不用刻意知道数组的长度,使用.length来获取数组的长度。
//for int[]array = new int[]{10, 20, 30, 40, 50}; for(int i = 0; i < array.length; i++){ System.out.println(array[i]); } //foreach int[] array = {1, 2, 3}; for (int x : array) { System.out.println(x); }
增强for循环是得不到数组的下标的,所以它一般用于数组的遍历,比如数组累加这样的操作。
三、数组在内存中的分布
1、JVM内存分布简介
要了解数组在内存里面的情况,就要知道Java内存分布是什么样的,这里做必要的介绍。Java经过编译后产生的.class文件被加载到JVM虚拟机里面的本地方法栈里面运行。为了高效管理内存,JVM对内存进行了划分。JVM是一个软件,由C/C++编写的软件。这是因为系统之类的由C/C++代码编写比较高效。
说明:
(1)Java虚拟机栈:也是我们在Java中常说栈。一般用来存放局部变量。
(2)本地方法栈:运行由c/c++编写的代码。经过编译产生的.class文件被加载到这里运行。
(3)堆:是Java中最大的一块内存空间。只要是对象,都是在堆上开辟的。在堆里面的引用叫对象。堆上的内存是不需要进行手动释放的,Java有自己的垃圾回收机制。
(4)程序计数器:保存一些指令和信息等。
(5)方法区:存放常量,静态成员变量等。
这里重点关心堆和虚拟机栈。
2、引用类型变量
引用类型创建的变量,一般称为对象的引用。存储的是对象所在空间的地址。如何理解数组的引用呢?比如写了这么一个代码:
int[] arr = new int[] {1,2,3}; System.out.println(arr);//[I@14514713
在内存中发生了什么呢?
这里的arr是局部变量,运行代码后,java就会在栈上为arr分配空间。后面new了之后,就会在堆上开辟一块空间来保存这些内容。arr存的是后面对象的地址。这里要强调的是,引用变量存的是对象的地址。
现在我们直接打印arr输出了:[I@14514713
打印出了这么一个地址(可以理解为数组首元素地址)。这里的地址为了安全,经过了特殊的处理,是这个引用对象的哈希地址。@之后的是哈希地址,@前的I表示这是一个int型,[表示是一个数组。arr这个引用,引用(指向)了一个数组对象。在比如以下代码:
int[] arr = new int[] { 1,2,3,4 }; int[] brr = arr;//??? System.out.println(arr);//[I@14514713 System.out.println(brr);//[I@14514713
这里打印出来的地址是一样的,说明brr也引用了与arr相同的对象。
四、二维数组
1、二维数组定义
二维数组本质上也就是一维数组,只不过每个元素又是一个一维数组。
数据类型 数组名称 = new 数据类型 行数 { 初始化数据 };
int arr1 = { {1,2,3},{4,5,6} }; int arr2 = new int { {1,2,3},{4,5,6} }; int arr3 = new int2; int arr4 = new int2; 在Java中,如果是前两种定义的方式,必须要手动加括号。同时,行是必须要指定的,列可以不用指定。
2、二维数组遍历
和一维数组类似,二维数组有for循环和foreach循环来进行遍历。
int[][] arr1 = { {1,2,3},{4,5,6} }; //for for (int i = 0; i < arr1.length; i++) { for (int j = 0; j < arr1[i].length; j++) { System.out.print(arr1[i][j] + " "); } System.out.println(); } //foreach for (int[] x : arr1) { for (int y : x) { System.out.print(y + " "); } System.out.println(); }
五、数组常用的方法
//导入包 import java.util.Arrays; public class Main { public static void main(String[] args) { //1、Arrays.toString方法 //将一维数组变成字符串。二维数组使用Arrays.deepToString方法。 int[] array=new int[]{1,2,3,4}; System.out.println(array);//[I@14514713 System.out.println(Arrays.toString(array));//[1, 2, 3, 4] //2.1、Arrays.copyOf方法 //从0下标来复制指定长度数组的内容到新的数组中。 int[] array1=Arrays.copyOf(array,2); System.out.println(Arrays.toString(array1));//[1,2] //2.2、Arrays.copyOfRange方法 //和Arrays.copfOf方法类似,这个是指定范围的拷贝。范围是左闭右开区间。 int[] array2=Arrays.copyOfRange(array,2,4); System.out.println(Arrays.toString(array2));//[3, 4] //3、Arrays.sort方法 //对数组进行升序排序。 int[] ret={2,1,4,3}; Arrays.sort(ret); System.out.println(Arrays.toString(ret));//[1, 2, 3, 4] //4、Arrays.fill方法 //对数组内容进行指定填充。 int[] ret1=new int[10]; Arrays.fill(ret1,6); System.out.println(Arrays.toString(ret1));//[6, 6, 6, 6, 6, 6, 6, 6, 6, 6] Arrays.fill(ret1,1,3,8);//左闭右开 System.out.println(Arrays.toString(ret1));//[6, 8, 8, 6, 6, 6, 6, 6, 6, 6] // 5、Arrays.equal方法 //判断两个数组的内容是否相同 int[] ret2={6, 8, 8, 6, 6, 6, 6, 6, 6, 6}; boolean equals = Arrays.equals(ret1, ret2); System.out.println(equals);//true // 6、Arrays.binarySearch方法 //二分查找数组内容,使用前先sort排序数组。 int[] ret3={4,1,3,2}; //先进行从小到大排序 Arrays.sort(ret3); //二分查找 int i = Arrays.binarySearch(ret3, 3); System.out.println(i);//返回索引2 } }