数组和Arrays类的基本知识

数组的三种创建方式

创建数组的三种方式:其实分为2类,一种是静态的创建,如方式一。一种是动态的创建,只不过根据写法的不同分为方式二和方式三:

public static void main(String[] args) {
	// 1.方式一  声明 分配空间并赋值
	int[] arr1 = {1,2,3};
	// 2.方式二 显示初始化
	int[] arr2;
	arr2 = new int[]{1,2,3}; 
	// 3.方式三 显示初始化()
	int[] arr3;
	arr3 = new int[3];
}

他们的区别,方式一:在声明的时候直接就已经分配空间,并赋值,方式一是不能写成如下这种形式的。

int[] arr1;
arr1 = {1,2,3};//错误写法 编译不同过

方式二和方式三,声明和内存分配是分开的,如上面的例子,

int[] arr2;int[] arr3;

这一步是在栈空间分配一个引用,存放的是一个引用,null

arr2 = new int[]{1,2,3};
arr3 = new int[3];

到这一步的时候jvm才开始在内存堆区域分配空间,并赋值,方式二直接赋值 1,2,3 方式三 默认初始化,基本类型是 0 布尔类型是 false 引用类型为null,

注:内存一旦分配不能改变,所有说数组长度固定

多维数组的遍历

对于一维数组
      最简单的遍历方法

for( int i =0; i<arrayName.length; i++)
{
Syetem.out.printf("arrayName[i]");
}

      foreach循环

java5之后,java提供了一种更为简单的循环,无需根据索引来访问数组元素,foreach循环自动遍历数组和集合的每个元素。

public class ForEachTest
{
public static void main (String [] args)
{
string[] books = {"1","2","3"};
for( String book : books)
{
System.out.println(book);
}
}
}

对于多维数组

Java中的二维数组其实是一个一维数组的数组,这意味着二维数组是一个数组的引用,其每一个元素都是另一个int数组的引用(多维数组依次),所以不同的遍历方式对性能的影响非常大

在这里插入图片描述

package arrayTraverse;
/**
 * 二维数组的问题
 * 
 * 我们在初始化一个任意大小的2维数组。(为简化分析我们使用二维方阵)我们将用两种不同方式迭代同一个数组,分析结果
 * 两种迭代方式的性能差距很大
 * @author mohit
 *
 */
public class TheProblemOf2DArray {
    //数组大小:数组越大,性能差距越明显
    private static final int ARR_SIZE=9999;
    public static void main(String[] args) {
        //新数组
        int arr[][]=new int[ARR_SIZE][ARR_SIZE];
        long currTime=System.currentTimeMillis();
        colMajor(arr); 
        System.out.println("Total time in colMajor : "+(System.currentTimeMillis()-currTime)+" ms");
        //新数组,与arr完全相同
        int arr1[][]=new int[ARR_SIZE][ARR_SIZE];
        currTime=System.currentTimeMillis();
        rowMajor(arr1); // this is the only difference in above
        System.out.println("Total time in col : "+(System.currentTimeMillis()-currTime) +" ms");
    }
 
    /**
     * 下面的代码按列为主遍历数组
     * 即在扫描下一行之前先扫描完本行
     * 
     */
    private static void colMajor(int arr[][]) {
        for(int i=0;i<ARR_SIZE;i++){
            for (int j=0;j<ARR_SIZE;j++){
                //See this, we are traversing j first and then i
                arr[i][j]=i+j;
            }
        }
    }
 
    /**
     * 如果我们转换内外循环
     * 程序就以行为主顺序遍历数组
     * 即在扫描下一列之前先扫描完本列
     * 这意味着我们访问数组时每次都在访问不同的行(因此也在访问不同的页)
     * 代码微小的改变将导致这个程序花费更多的时间完成遍历
     */
    private static void rowMajor(int arr[][]) {
        for(int i=0;i<ARR_SIZE;i++){
            for (int j=0;j<ARR_SIZE;j++){
            /*看这个,我们先遍历j,然后遍历i,但是对于访问元素来说
             * 它们在更远的位置,所以需要花费的更多
             */
            arr[j][i]=i+j;
            }
        }
    }
}

Arrays类的常用方法

asList()

  • Arrays.asList(T… data)

注意:该方法返回的是Arrays内部静态类ArrayList,而不是我们平常使用的ArrayList,,该静态类ArrayList没有覆盖父类的add, remove等方法,所以如果直接调用,会报UnsupportedOperationException异常

  • 将数组转换为集合,接收一个可变参
List<Integer> list = Arrays.asList(1, 2, 3);
list.forEach(System.out::println); // 1 2 3
Integer[] data = {1, 2, 3};
List<Integer> list = Arrays.asList(data);
list.forEach(System.out::println); // 1 2 3
  • 如果将基本数据类型的数组作为参数传入

该方法会把整个数组当作返回的List中的第一个元素

int[] data = {1, 2, 3};
List<int[]> list = Arrays.asList(data);
System.out.println(list.size()); // 1
System.out.println(Arrays.toString(list.get(0))); // [1, 2, 3]

copyOf()

  • Arrays.copyOf(T[] original, int newLength)
  • 拷贝数组,其内部调用了 System.arraycopy() 方法,从下标0开始,如果超过原数组长度,会用null进行填充
Integer[] data1 = {1, 2, 3, 4};
Integer[] data2 = Arrays.copyOf(data1, 2);
System.out.println(Arrays.toString(data2)); // [1, 2]
Integer[] data2 = Arrays.copyOf(data1, 5);
System.out.println(Arrays.toString(data2)); // [1, 2, 3, 4, null]

copyOfRange

  • Arrays.copyOfRange(T[] original, int from, int to)
  • 拷贝数组,指定起始位置和结束位置,如果超过原数组长度,会用null进行填充
Integer[] data1 = {1, 2, 3, 4};
Integer[] data2 = Arrays.copyOfRange(data1, 0, 2);
System.out.println(Arrays.toString(data2)); // [1, 2]
Integer[] data2 = Arrays.copyOfRange(data1, 0, 5);
System.out.println(Arrays.toString(data2)); // [1, 2, 3, 4, null]

sort()

  • Arrays.sort(Object[] array)
  • 对数组元素进行排序(串行排序)
String[] data = {"1", "4", "3", "2"};
System.out.println(Arrays.toString(data)); // [1, 4, 3, 2]
Arrays.sort(data);
System.out.println(Arrays.toString(data)); // [1, 2, 3, 4]
  • Arrays.sort(T[] array, Comparator<? super T> comparator)
  • 使用自定义比较器,对数组元素进行排序(串行排序)
String[] data = {"1", "4", "3", "2"};
System.out.println(Arrays.toString(data)); // [1, 4, 3, 2]
// 实现降序排序,返回-1放左边,1放右边,0保持不变
Arrays.sort(data, (str1, str2) -> {
    if (str1.compareTo(str2) > 0) {
        return -1;
    } else {
        return 1;
    }
});
System.out.println(Arrays.toString(data)); // [4, 3, 2, 1]

lambda注:表达式可能在某些低版本编译器编译不通过

  • Arrays.sort(Object[] array, int fromIndex, int toIndex)
  • 对数组元素的指定范围进行排序(串行排序)
String[] data = {"1", "4", "3", "2"};
System.out.println(Arrays.toString(data)); // [1, 4, 3, 2]
// 对下标[0, 3)的元素进行排序,即对1,4,3进行排序,2保持不变
Arrays.sort(data, 0, 3);
System.out.println(Arrays.toString(data)); // [1, 3, 4, 2]
  • Arrays.sort(T[] array, int fromIndex, int toIndex, Comparator<? super T> c)
  • 使用自定义比较器,对数组元素的指定范围进行排序(串行排序)

toString()

  • Arrays.toString(Object[] array)
  • 返回数组元素的字符串形式
Integer[] data = {1, 2, 3};
System.out.println(Arrays.toString(data)); // [1, 2, 3]

fill()

  • Arrays.fill(Object[] array, Object obj)
  • 用指定元素填充整个数组(会替换掉数组中原来的元素)
Integer[] data = {1, 2, 3, 4};
Arrays.fill(data, 9);
System.out.println(Arrays.toString(data)); // [9, 9, 9, 9]
  • Arrays.fill(Object[] array, int fromIndex, int toIndex, Object obj)
  • 用指定元素填充数组,从起始位置到结束位置,取头不取尾(会替换掉数组中原来的元素)
Integer[] data = {1, 2, 3, 4};
Arrays.fill(data, 0, 2, 9);
System.out.println(Arrays.toString(data)); // [9, 9, 3, 4]
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值