Java数组,堆栈,Arrays工具类
数组的使用
- 数组的定义
概述:数组是多个相同类型数据的组合,实现对这些数据的统一管理,数组属引用类型,数组型数据是对象(Object),数组中的每个元素相当于该对象的成员变量,数组中的元素可以是任何数据类型,包括基本类型和引用类型。
作用:是用来存储固定大小的同类型元素。
定义:
(1)数据类型[ ] 变量名;例:int[ ] arr;
(2)数据类型 变量名[ ] ;例:int arr[ ];
创建:
Java语言使用new操作符来创建数组,语法如下:
数据类型[ ] 变量名=new 数据类型[数组长度] ;
例:int[ ] arr=new int[50];//定义一个长度为50的int数组。
或者直接在创建的时候赋予初值,语法如下:
数据类型[ ] 变量名={值1,值2,值3,值4};
例:int[ ] arr={1,2,8,98};(不推荐 建议每次声明都声明好数据类型)
处理:数组的元素类型和数组的大小都是确定的,所以当处理数组元素时候,我们通常使用基本循环或者 foreach 循环。
数组元素的默认初始化:数组是引用类型,它的元素相当于类的成员变量,因此数组一经分配空间,其中的每个元素也被按照成员变量同样的方式被隐式初始化。
如果定义了数组:
int[] a = new int[] {1,2,3,4,5,};}
int[] b = new int[] {1,2,3,4,5};}
a,b数组的长度是一样的 不会因为末尾的逗号增加长度
- 数组的遍历
通常使用常规循环 或者 foreach循环遍历数组
foreach:
@Test
public void test1() {
int[] a = new int[] {1,2,34,4,5,6,7};
for (int b:
a) {
System.out.println(b);
}
}
for循环省略。如果想通过循环来修改数组的值,只能用常规循环,foreach循环只能遍历输出数组,无法修改或者删除数组,若在foreach中修改了i值,只是修改了临时变量的值,没有对数组进行操作。
注:新建数组时一定要有类型和大小!
数组默认初始化的值如下:
1. 数值类的数组初始化默认为0或者0.0
2. bool类的数组初始化默认为false
3. 引用类型数组初始化默认都是null
完整图:
**注:null可以赋值给引用类型,但是不可以赋值给基本类型。
注:null在sout中无法输出的原因是:null在sout方法中既可以匹配到char[], 也可以匹配到String类型,编译器无法进行输出。**
例子:
public class Demo3Test {
public static void exchangenum(int a,int b){
int temp;
temp = a;
a = b;
b = temp;
System.out.println("a:" + a + ",b:" + b);
}
public static void exchangenumarray(int[] a){
int temp;
temp = a[0];
a[0] = a[1];
a[1] = temp;
System.out.println("a[0]:" + a[0] + ",a[1]:" + a[1]);
}
@Test
public void test1() {
int a = 10;
int b = 20;
int c[] = new int[]{10,20};
exchangenum(a,b);
exchangenumarray(c);
}
}
若将自己写的两个方法中的sout写到main函数中,则只有数组交换的方法会起作用
因为int是基本数据类型,在java虚拟机中是栈输出,无法交换
int[]是引用数据类型,在java虚拟机中直接将数值地址上的值进行交换,因此int[]型的可以直接交换。
java jvm 堆 栈
##可变参数长度
- 它的本质还是数组,调用时可以用数组或多个实参
- 可变参数只能有一个,且必须放置在参数列表的最后
- 当我们不传参数时,默认自动封装的数组是长度为0的数组,如果强制打印该数组的值,会发生下标越界的错误
例子:
若将一个数组中的数字进行寻找最大值
可以轻易地写出来方法,但是如果需要在数组中的数字与额外的数字比较呢? 这个时候就要用可变参数
public static int getMax(int... arr){
int temp = arr[0];
for (int i = 1; i < arr.length; i++) {
temp = (temp>arr[i])?temp:arr[i];
}
return temp;
}
@Test
public void test2(){
int[] a = {1,2,3,4,45,6,6,7};
int s1 = 1;
int s2 = 2;
int s3 = 8;
int s4 = 7;
int s5 = 6;
int c = 0;
System.out.println(getMax(s1,s2,s3,s4,s5,c));
System.out.println(getMax(a));
}
从这个方法可以看出 可以使用长度可变的参数进行使用,比数组更加快捷
但是也有一些不足
比如说如果没有传入值,强制进行打印会出现数组下标越界的异常 应该在代码中添加判断,并且通过异常处理,因为返回值可能影响到其他的模块。
还可以添加一个boolean类型的参数,用于判断要求最大值还是最小值,此参数要写在可变长度参数之前。
因此 修改后的代码为:
public static int getMax(boolean max,int... arr){
int temp = arr[0];
if(max){
for (int i = 1; i < arr.length; i++) {
temp = (temp>arr[i])?temp:arr[i];
}
}
if(!max){
for (int i = 1; i < arr.length; i++) {
temp = (temp<arr[i])?temp:arr[i];
}
}
return temp;
}
@Test
public void test2(){
int[] a = {1,2,3,4,45,6,6,7};
int s1 = 1;
int s2 = 2;
int s3 = 8;
int s4 = 7;
int s5 = 6;
int c = 0;
System.out.println(getMax(true,s1,s2,s3,s4,s5,c));
System.out.println(getMax(false,s1,s2,s3,s4,s5,c));
System.out.println(getMax(true,a));
System.out.println(getMax(false,a));
}
听课的原笔记:
Arrays工具类
- 手写一个数组复制的方法 低效率而且时间长 可以使用System.arraycopy()方法
- 数组排序手写方法很麻烦,可以使用Arrays.sort方法
- 数组初始化不想全都是0,可以使用Arrays.fill方法
代码如下:
@Test
public void test3(){
int[]a = new int[]{2,1,5,3,8,9,7,8,6};
int[]b = new int[a.length+a.length/2];
System.out.print("a数组排序前:");
for (int i:
a) {
System.out.print(i + "\t");
}
System.out.println();
Arrays.sort(a);
System.out.print("a数组排序后:");
for (int i:
a) {
System.out.print(i +"\t");
};
System.out.println();
System.arraycopy(a,1,b,4,4);
//从a数组的第1+1个元素开始复制元素到b数组的第4+1处,共复制4个
System.out.print("a数组复制后的b数组:");
for (int i:
b) {
System.out.print(i + "\t");
}
System.out.println();
//用Arrays.fill初始化数组:
int[] c = new int[5];
Arrays.fill(c, 1);
System.out.print("初始化后:");
for (int i:
c) {
System.out.print(i + "\t");
}
System.out.println();
}