标签:
看到Object的clone()是protected的,然后看到《java2认证考试指南》上描述:一个对象只能请求其他对象的克隆,后者的类与被克隆对象属于同一类,或是被克隆对象的子类。
example: C-->B-->A <--D
C对象能克隆B或A对象;B对象能克隆A对象;D对象能克隆A对象
B对象不能克隆D对象
我是读了很久没有理解,最后读了一些程序才发现这样理解:主要是visibility问题。因为是protected的,那么在子类不重载,则自动继承。子类和父类在不同package时,子类实例可以调用它自己的protected foo(), 但在子类的code中调用父类实例的protected foo(),则看不见。 //子类中用父类对象反而不能访问父类中的protected变量
之所以没能理解,原因居然是国内的很多Java书籍在介绍访问权限时,一般都这样描述:
public | protected | default | private | |
同类 | T | T | T | T |
同包 | T | T | T | |
子类(不同包) | T | T | ||
无继承关系不同包的类 | T |
所以我们想当然的认为,B继承A,在不同包,那么在B的code中用A的实例a调用a.clone()是可以的,但是,事实上:不行(但b.clone显然可以)
代码如下:
package test; public class Tree{ protected int age; void sayTree(){ Maple mm=new Maple(); mm.clone();//compile ok, mm is instance of Maple, also instance of Tree } } class Maple extends Tree{ public void sayMaple(){ Maple m=new Maple(); m.age=0; Tree t=new Tree(); t.age=0; //ok, same pack can access protected field m.clone();//compile ok, can access Maple‘s protected fun t.clone();//error, t is instance of Tree, but not instance of Maple!-----------见上文黑色粗体字 } } package test.a; import test.*; class Pine extends Tree{ public void say(){ Pine p=new Pine(); p.age=0; p.clone(); Tree t=new Tree(); t.age=0; // invisible t.clone(); // invisible } }
标签:
原文地址:http://www.cnblogs.com/jack-xu/p/4882944.html