温馨提示×

温馨提示×

您好,登录后才能下订单哦!

密码登录×
登录注册×
其他方式登录
点击 登录注册 即表示同意《亿速云用户服务条款》

Java数组的拷贝方式有哪些

发布时间:2022-02-24 09:35:35 来源:亿速云 阅读:172 作者:小新 栏目:开发技术

这篇文章主要介绍了Java数组的拷贝方式有哪些,具有一定借鉴价值,感兴趣的朋友可以参考下,希望大家阅读完这篇文章之后大有收获,下面让小编带着大家一起了解一下。

    深拷贝与浅拷贝的区别

    假设现在有原数组A以及拷贝后的数组B,若是改变A中的某一个值,B数组随之相应的发生变化的拷贝方式称为浅拷贝,反之B数组不受影响,则称为深拷贝;
    简单总结一下两者的概念:

    深拷贝:拷贝后,修改原数组,不会影响到新数组;

    浅拷贝:拷贝后,修改原数组,新数组也会相应的发生改变;

    1. for循环进行拷贝

    拷贝数值类型

    当数组中存放的元素为基本数据类型时,此时发生的是深拷贝;

    //1. for循环拷贝  (拷贝数值类型) ---深拷贝
        public static void main(String[] args) {
            int[] A = {1,2,3,4,5};
            int[] B = new int[A.length];
            for (int i = 0; i < A.length; i++) {
                B[i] = A[i];
            }
            System.out.println("A : " + Arrays.toString(A));  //A : [1, 2, 3, 4, 5]
            System.out.println("B : " + Arrays.toString(B));  //B : [1, 2, 3, 4, 5]
            System.out.println("===========修改后===========");
            A[0] = 100;
            System.out.println("A : " + Arrays.toString(A));  //A : [100, 2, 3, 4, 5]
            System.out.println("B : " + Arrays.toString(B));  //B : [1, 2, 3, 4, 5]
        }
        //打印对象数组的方法
        public static void show(Num[] arrays) {
            for (int i = 0; i < arrays.length; i++) {
                System.out.print(arrays[i].getVal() + " ");
            }
            System.out.println();
        }
    class Num{
        public int val = 0;
    
        public Num(int val) {
            this.val = val;
        }
    
        public int getVal() {
            return val;
        }
    
        public void setVal(int val) {
            this.val = val;
        }
    }

    拷贝引用类型

    当数组中存放的元素为引用数据类型时,此时发生的是浅拷贝;

    //1. for循环拷贝  (拷贝引用数据类型) ---浅拷贝
        public static void main(String[] args) {
            Num[] A = new Num[4];
            A[0] = new Num(1);
            A[1] = new Num(2);
            A[2] = new Num(3);
            A[3] = new Num(4);
            Num[] B = new Num[4];
            for (int i = 0; i < A.length; i++) {
                B[i] = A[i];
            }
            show(A);  //1 2 3 4 
            show(B);  //1 2 3 4 
            System.out.println("===========修改后===========");
            A[0].setVal(100);
            show(A);  //100 2 3 4
            show(B);  //100 2 3 4
        }

    2. copyof / copyOfRange

    拷贝数值类型

    当数组中存放的元素为基本数据类型时,此时发生的是深拷贝;

    Arrays.copy(原数组,自定义新数组长度);

    Arrays.copyOfRange(原数组,from,to);

    注意拷贝截取的范围是左闭右开的[from,to)

    //2. copy / copyOfRange  (拷贝数值类型) ---深拷贝
        public static void main(String[] args) {
            int[] A = {1,2,3,4,5};
            int[] B = Arrays.copyOf(A,A.length);
            int[] C = Arrays.copyOfRange(A,1,3);
            System.out.println("A : " + Arrays.toString(A));  //A : [1, 2, 3, 4, 5]
            System.out.println("B : " + Arrays.toString(B));  //B : [1, 2, 3, 4, 5]
            System.out.println("C : " + Arrays.toString(C));  //C : [2, 3]
            System.out.println("===========修改后===========");
            A[0] = 100;
            System.out.println("A : " + Arrays.toString(A));  //A : [100, 2, 3, 4, 5]
            System.out.println("B : " + Arrays.toString(B));  //B : [1, 2, 3, 4, 5]
            System.out.println("C : " + Arrays.toString(C));  //C : [2, 3]
        }

    拷贝引用类型

    当数组中存放的元素为类的对象时,此时发生的是浅拷贝;

    //2. copy / copyOfRange  (拷贝引用类型) ---浅拷贝
        public static void main(String[] args) {
            Num[] A = new Num[4];
            A[0] = new Num(1);
            A[1] = new Num(2);
            A[2] = new Num(3);
            A[3] = new Num(4);
            Num[] B = Arrays.copyOf(A,A.length);
            show(A);  //1 2 3 4
            show(B);  //1 2 3 4
            System.out.println("===========修改后===========");
            A[0].setVal(100);
            show(A);  //100 2 3 4
            show(B);  //100 2 3 4
        }
    class Num{
        public int val = 0;
    
        public Num(int val) {
            this.val = val;
        }
    
        public int getVal() {
            return val;
        }
    
        public void setVal(int val) {
            this.val = val;
        }
    }

    3. arraycopy

    拷贝数值类型

    当数组中存放的元素为基本数据类型时,此时发生的是深拷贝;

    System.arraycopy(src, srcPos dest, destPos, length);

    其中各个参数分别表示 如下:

    • src :源数组

    • srcPos:源数组要复制的起始位置

    • dest:目标数组

    • destPos:目标数组复制的起始位置

    • length:复制的长度

    所以srcPos和destPos都为0,且length为源数组长度时,表示完完整整的拷贝过来了;那么截取范围拷贝也举个例子,下面的代码中srcPos = 1,destPos = 2,length = 2,表示从A数组下标为1的位置开始截取2个元素,放到B数组中下标为2的位置作为起始位置,再对比一下输出看看。

    //3. arraycopy  (拷贝数值类型) ---深拷贝
        public static void main(String[] args) {
            int[] A = {1,2,3,4,5};
            int[] B = new int[A.length];
            //System.arraycopy(A,0,B,0,A.length);
            System.arraycopy(A,1,B,2,2);
            System.out.println("A : " + Arrays.toString(A));  //A : [1, 2, 3, 4, 5]
            System.out.println("B : " + Arrays.toString(B));  //B : [0, 0, 2, 3, 0]
            System.out.println("===========修改后===========");
            A[0] = 100;
            System.out.println("A : " + Arrays.toString(A));  //A : [100, 2, 3, 4, 5]
            System.out.println("B : " + Arrays.toString(B));  //B : [0, 0, 2, 3, 0]
        }

    拷贝引用类型

    当数组中存放的元素为类的对象时,此时发生的是浅拷贝;

    //3. arraycopy  (拷贝引用类型) ---浅拷贝
        public static void main(String[] args) {
            Num[] A = new Num[4];
            A[0] = new Num(1);
            A[1] = new Num(2);
            A[2] = new Num(3);
            A[3] = new Num(4);
            Num[] B = new Num[4];
            System.arraycopy(A,0,B,0,A.length);
            show(A);  //1 2 3 4
            show(B);  //1 2 3 4
            System.out.println("===========修改后===========");
            A[0].setVal(100);
            show(A);  //100 2 3 4
            show(B);  //100 2 3 4
        }
    class Num{
        public int val = 0;
    
        public Num(int val) {
            this.val = val;
        }
    
        public int getVal() {
            return val;
        }
    
        public void setVal(int val) {
            this.val = val;
        }
    }

    4. clone

    拷贝数值类型

    当数组中存放的元素为基本数据类型时,此时发生的是深拷贝;

    //4. clone  (拷贝数值类型) ---深拷贝
        public static void main(String[] args) {
            int[] A = {1,2,3,4,5};
            int[] B = A.clone();
            System.out.println("A : " + Arrays.toString(A));  //A : [1, 2, 3, 4, 5]
            System.out.println("B : " + Arrays.toString(B));  //B : [1, 2, 3, 4, 5]
            System.out.println("===========修改后===========");
            A[0] = 100;
            System.out.println("A : " + Arrays.toString(A));  //A : [100, 2, 3, 4, 5]
            System.out.println("B : " + Arrays.toString(B));  //B : [1, 2, 3, 4, 5]
        }

    拷贝引用类型

    当数组中存放的元素为类的对象时,此时发生的是浅拷贝;

    //4. clone  (拷贝引用类型) ---浅拷贝
        public static void main(String[] args) {
            Num[] A = new Num[4];
            A[0] = new Num(1);
            A[1] = new Num(2);
            A[2] = new Num(3);
            A[3] = new Num(4);
            Num[] B = A.clone();
            show(A);  //1 2 3 4
            show(B);  //1 2 3 4
            System.out.println("===========修改后===========");
            A[0].setVal(100);
            show(A);  //100 2 3 4
            show(B);  //100 2 3 4
        }

    5. 总结

    拷贝方式数值类型引用类型推荐使用
    for循环深拷贝浅拷贝 
    copyof深拷贝浅拷贝&radic;
    arraycopy深拷贝浅拷贝&radic;
    clone深拷贝浅拷贝 

    由于arraycopy底层是C++写的,所以速度快,更多的是使用这个方法。

    注意:本文中所有的引用数据类型都是以类的对象为例,使用的是对象数组,我们也知道引用类型包括类,接口,字符串等等。但是需要注意字符串是新的变量,所以如果是连个字符串数组进行拷贝,即使他们是引用类型,但是每次都会创建了一个字符串数组对象, 因此, 修改原数组, 不会影响到新数组,即深拷贝。

    感谢你能够认真阅读完这篇文章,希望小编分享的“Java数组的拷贝方式有哪些”这篇文章对大家有帮助,同时也希望大家多多支持亿速云,关注亿速云行业资讯频道,更多相关知识等着你来学习!

    向AI问一下细节

    免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。

    AI