美文网首页技术文首页投稿(暂停使用,暂停投稿)程序员
Java中数组有对应的类么?为什么数组可以直接调用clone()

Java中数组有对应的类么?为什么数组可以直接调用clone()

作者: 阿菜的博客 | 来源:发表于2016-10-21 15:41 被阅读114次
Java中数组有对应的类么

该问题从clone()方法开始引出。

clone()是基类Object类中的一个protected方法。

对该方法做以下测试。

问题所在:https://segmentfault.com/q/1010000007236444

1. 在类A中调用类A实例a的clone()方法

public class A implements Cloneable {
    public static void main(String[] args) throws CloneNotSupportedException {
        A a = new A();
        // 调用正确
        A a2 = (A) a.clone();
    }
}

以上调用成功,因为A是object的子类,继承了Object中的clone()方法,所以可以直接调用。

2. 在类B中调用类A实例a的clone()方法

public class B {
    public static void main(String[] args) {
        A a = new A();
        // 调用失败
        a.clone();
    }
}

错误信息:

方法不可见

以上调用出错,A和B都是Object的子类,都继承了clone()方法,但不能在一个子类中调用另一个子类的protected方法。

如果需要在类B中实现对实例a的clone,类A需要重写clone方法,并且申明为public,如下:

类A:

public class A implements Cloneable {
    public Object clone() throws CloneNotSupportedException {
        return super.clone();
    }
}

类B:

public class B {
    public static void main(String[] args) throws CloneNotSupportedException {
        A a = new A();
        // 调用成功
        a.clone();
    }
}

以上调用成功,因为类A重写了clone方法,并且申明为public。

3. 提出问题,数组为什么可以直接调用clone()方法

public class ArrayClone {
    public static void main(String[] args) {
        int[] array = {1, 1, 4, 7};
        // 调用成功
        array.clone();
    }
}

如果把array理解成为Object的子类,那么该array应该不能在类ArrayClone中调用clone()方法。但是可以调用成功。

此外:

章节1中,直接在类A中调用实例a的clone()方法时,IDE明确指出clone()方法是protected的,智能提示上有个小钥匙。


小钥匙

而在章节3中,调用数组的clone()方法时,IDE提示该方法是public的,智能提示上有个打开的锁。


打开的锁

4. 提问

1. Java中是否有一个类对应数组?数组在jvm中是一个怎样的存在?
2. 数组的clone()方法是怎么实现的?为什么可以直接调用?为什么是public的?
3. 数组的.length方法是怎么实现的?为什么IDE点不进去源码?

5. 参考

一些参考,可能对可能不对的解释。

  1. 其实是有对应的类的,但不是Java的类,是JVM编译的时候实现的。
  2. 这个类的命名,如int数组为[I,如String数组为[Ljava.lang.String;,如A数组为[Ltest.cloneTest.A;
  3. 用.getClass().getName()和.getClass().getInterfaces()即可知道该特殊类的类名和该类实现的接口。
  4. 得到该类实现了Cloneable和Serializable接口。和Object中写明的Note that all arrays are considered to implement the interface Cloneable吻合。
  5. 猜测是Java编译器允许的数组定义的语法糖,其实JVM会生成一个类,该类实现了Cloneable和Serializable接口,并且有一个public的clone()方法,可以在其他类中直接调用。(其实没有这个方法,可以通过.get.getMethods()进行验证)
  6. 至于数组的length属性,可能是直接保存在这个特殊的类的类头部中了,毕竟数组长度是不能修改的,直接保存着是完全符合逻辑的。

相关文章

网友评论

    本文标题:Java中数组有对应的类么?为什么数组可以直接调用clone()

    本文链接:https://www.haomeiwen.com/subject/tlhcuttx.html