zoukankan      html  css  js  c++  java
  • Java 隐藏和覆盖

    我们知道,在JAVA中,子类可以继承父类,如果子类声明的方法与父类有重名的情况怎么办,大伙儿都知道要是重写,但是实际上这又分为两种情况,就是方法和变量在继承时的覆盖和隐藏问题,这些概念性的东西看似无聊,但是在面试或者是SCJP认证题中围绕这些是会经常碰到的,所以这里来讨论下

    首先我们来看几个概念

    隐藏 :child隐藏了parent的变量和方法,那么,child不能访问parent被隐藏的变量或者方法,但是,讲B转换成A中,可以访问A被隐藏的变量或者方法

    覆盖 :child覆盖了parent的变量或者方法,那么,child不能访问parent被覆盖的变量或者方法,将child转换成parent后同样不能访问parent被覆盖的变量或者方法

    首先看一下JAVA中方法和变量在继承时的覆盖和隐藏规则

    1.父类的实例变量和静态变量能被子类的同名变量隐藏

    2.父类的静态方法被子类的同名静态方法隐藏

    3.父类的实例方法被子类的同名实例变量覆盖

    还有几点需要注意的是

    1.不能用子类的静态方法隐藏 父类中同样标示(也就是返回值 名字 参数都一样)的实例方法

    2.不能用子类的实例方法覆盖 父类中同样标示的静态方法

    3.这点儿请注意,就是变量只会被隐藏 不会被覆盖 ,无论他是实例变量还是静态变量,而且,子类的静态变量可以隐藏 父类的实例变量,子类的实例变量可以隐藏 父类的静态变量

    O(∩_∩)O哈哈~ 是不是有点儿绕口,没关系 我们看一个实例

    创建两个父子类关系的类

    Java代码  收藏代码
    1. //父类  
    2. class Parent  
    3. {  
    4.     public static String kind="javastudy.extendsstudy.parent";  
    5.     public static int age=50;  
    6.     public String name="Parent";  
    7.   
    8.     //静态方法,返回包名  
    9.     public static String getKind()  
    10.     {  
    11.         System.out.println("parent的getKind()方法被调用了");  
    12.         return kind;  
    13.     }  
    14.   
    15.     //静态方法,返回年龄  
    16.     public static int getAge()  
    17.     {  
    18.         System.out.println("Parent的getAge()方法被调用了");  
    19.         return age;  
    20.     }  
    21.   
    22.     //实例方法,返回姓名  
    23.     public String getName()  
    24.     {  
    25.         System.out.println("Parent的getName()方法被调用了");  
    26.         return this.name;  
    27.     }  
    28.   
    29. }  
    30.   
    31.   
    32. //子类  
    33. class Child extends Parent  
    34. {  
    35.     public static String kind="javastudy.extendsstudy.child";  
    36.     public int age=25;  
    37.     public String name="child";  
    38.   
    39.     //隐藏父类静态方法  
    40.     public static String getKind()  
    41.     {  
    42.         System.out.println("child的getkind()方法被调用了");  
    43.         return kind;  
    44.     }  
    45.       
    46.     //获取父类包名  
    47.     public static String getParentKind()  
    48.     {  
    49.         return Parent.kind;  
    50.     }  
    51.       
    52.     //覆盖父类实例方法  
    53.     public String getName()  
    54.     {  
    55.         System.out.println("child的getName()被调用了");  
    56.         return this.name;  
    57.     }  
    58.       
    59.     //获取父类名称  
    60.     public String getParentName()  
    61.     {  
    62.         return super.name;  
    63.     }  
    64.     /* 
    65.      *错误,实例方法不能覆盖父类的静态方法 
    66.     public int getAge() 
    67.     { 
    68.         return this.age; 
    69.     } 
    70.     */  
    71. }  

     然后测试下

    Java代码  收藏代码
    1. class Test   
    2. {  
    3.     public static void main(String[] args)   
    4.     {  
    5.         Child child=new Child();  
    6.         System.out.printf("子类名称:%s,年龄:%d,包名:%s%n",child.name,child.age,child.kind);  
    7.         //输出:子类名称:child,年龄:25,包:javastudy.extendsstudy.child  
    8.   
    9.         //把child转换成parent对象  
    10.         Parent parent=child;  
    11.   
    12.         System.out.printf("转换后的名称:%s,年龄:%d,包名:%s%n",parent.name,parent.age,parent.kind);  
    13.         //输出:转换后的名称:Parent,年龄:50,包:javastudy.extendsstudy.parent  
    14.   
    15.         System.out.printf("子类访问父类被隐藏的实例变量name:%s%n",child.getParentName());  
    16.         //输出:子类访问父类被隐藏的实例变量name:Parent  
    17.           
    18.         System.out.printf("子类访问父类被隐藏的静态变量kind:%s",child.getParentKind());  
    19.         //输出:子类访问父类被隐藏的静态变量kind:javastudy.extendsstudy.parent  
    20.   
    21.         child.getName();  
    22.         //输出:child的getName()被调用了  
    23.   
    24.         //**************注意看这个方法,返回的还是子类的getName  
    25.         parent.getName();  
    26.         //输出:child的getName()被调用了  
    27.   
    28.         child.getKind();  
    29.         //输出:child的getkind()方法被调用了  
    30.   
    31.         parent.getKind();  
    32.         //输出:parent的getKind()方法被调用了  
    33.     }  
    34. }  

     好了,看了结果后总结下吧

    1.同名的实例方法被覆盖 ,同名的静态方法被隐藏 ,child类的getName实例方法覆盖 了parent的getName实例方法,chind的getKind方法隐藏 了parent类的getKind方法

    2.隐藏 和覆盖 的区别在于,子类对象转换成父类对象后,能够访问父类被隐藏 的变量和方法,而不能访问父类被覆盖 的方法

    3.如果需要访问父类被隐藏 的实例变量,加上super就好了,比如访问父类的name,写上super.name就好了

    本文不是教会大家重写父类变量的,而是重点说明方法和变量的隐藏和覆盖,这些个小知识点虽然在做项目的时候不怎么会用到,但是一定要记住,不然的话很多错误会感到莫名其妙,还有就是SCJP的题库里这类题大大存在,所以本人觉得这些细小的知识还是记住为好

  • 相关阅读:
    Azure DevOps上使用git push --force遇到的问题
    Redis常用的一些基本命令
    [Vue warn]: Error in v-on handler: "TypeError: this.onConfirm(...).then is not a function"
    政采云:数据可视化探索之SpreadJS 表格控件
    用Java写一个折半查找
    springboot 集成hibernate 多数据源链接
    java 自定义注解
    幻读:听说有人认为我是被MVCC干掉的
    懵了!女朋友突然问我MVCC实现原理
    不会MySQL索引,面试官让回家等通知!
  • 原文地址:https://www.cnblogs.com/ziq711/p/5603767.html
Copyright © 2011-2022 走看看