域名备案怎么关闭网站,鞍山网站制作小程序,做兼职拍照片传网站,网页源代码翻译器Java之private修饰成员方法默认是final型的#xff1f; private修饰的成员方法默认是final型的#xff1f; 用fianl声明的成员方法是最终方法#xff0c;最终方法不能被子类覆盖#xff08;重写#xff09;
从表面上看这个命题是错误的#xff0c;private访问修饰符修饰…Java之private修饰成员方法默认是final型的 private修饰的成员方法默认是final型的 用fianl声明的成员方法是最终方法最终方法不能被子类覆盖重写
从表面上看这个命题是错误的private访问修饰符修饰的成员方法怎么会跟final型方法有关系呢但从最终方法的定义可以看出不能被子类覆盖的成员方法就是最终方法而private修饰的成员方法就不能被子类覆盖证明如下
//证明private修饰的成员方法不能被子类覆盖
class Father{int m 0;private void set() {m 1;}public Father() {set();}
}
public class Son extends Father{private void set() {m 3;}public static void main(String[] args) {Father f new Son();System.out.println(f.m);}
} 输出3 分析 如果private修饰的set()方法被子类重写了当执行到 Father f new Son(); 语句先执行Father类的构造方法而构造方法的set()方法会调用子类的set()方法多态的一种表现输出结果为1 而实际输出的结果为3因此private修饰的成员方法没有被子类覆盖也就是说private修饰的成员方法默认是final型的。
在class文件中有专门描述方法的方法表方法表第一项就是访问标志access_flags。其中标志值为0x0001的 ACC_PRIVATE代表方法为private标志值为0x0002的 ACC_PUBLIC代表方法为方法为final可以通过判断access_flags的值判断方法有哪些访问标志。
public class Test {private void test(){}private final void test2(){}
}通过jclasslib bytecode viewer看出如下图 分析 两个方法一个是只有private修饰另一个是有private和final 修饰如果private修饰的成员方法默认是final型的那两个方法的access_flags值应该一样的可结果并非如此由此可以说明private修饰的成员方法默认是final型的是错误的。 如何理解 :类中所有的private方法都隐式的指定为是final的 为什么这么说有理论依据么 正解这段话来自《Java编程思想》多态那一章节的确不太明白作者为什么要这样子去说。 这种说法完全没有根据属于误人子弟 private和final没关系是两回事 拿属性来说可能更容易理解一些虽然private不能访问但通过反射修改访问权限还是可以访问修改的但加了final即使可以访问了也修改不了值这就是区别 自己用反射打印一下结果就知道了或者用javap反编译看一下伪代码 public class Sample {static class ATest {private void test1() {}private final void test2() {}}public static void main(String[] args) {try {Class? c Sample.ATest.class;Method f1 c.getDeclaredMethod(test1, null);System.out.printf(%s:%d\n, f1.getName(), f1.getModifiers()); //private修饰Method f2 c.getDeclaredMethod(test2, null);System.out.printf(%s:%d\n, f2.getName(), f2.getModifiers()); //private final修饰System.out.printf(private:%d\n, Modifier.PRIVATE); //private的修饰值System.out.printf(final:%d\n, Modifier.FINAL); //final的修饰值System.out.printf(private final:%d\n, Modifier.PRIVATE|Modifier.FINAL); //private和final一起的修饰值} catch (Throwable e) {e.printStackTrace();}}
}