JAVA中方法和变量在继承中的覆盖和隐藏(一)
我们知道,在JAVA中,子类可以继承父类,如果子类声明的方法与父类有重名的情况怎么办,大伙儿都知道要是重写,但是实际上这又分为两种情况,就是方法和变量在继承时的覆盖和隐藏问题,这些概念性的东西看似无聊,但是在面试或者是SCJP认证题中围绕这些是会经常碰到的,所以这里来讨论下
首先我们来看几个概念
类变量:又叫静态变量,这种变量属于类,通过类名就可以访问类变量。
实例变量:属于类的实例,即对象,通过对象可以访问实例变量,但是不能通过类名访问实例变量。
静态方法:通过类名访问。
实例方法:对象访问,不能通过类名访问。
隐藏 :child隐藏了parent的变量和方法,那么,child不能访问parent被隐藏的变量或者方法,但是,将B转换成A中,可以访问A被隐藏的变量或者方法
覆盖 :child覆盖了parent的变量或者方法,那么,child不能访问parent被覆盖的变量或者方法,将child转换成parent后同样不能访问parent被覆盖的变量或者方法
首先看一下JAVA中方法和变量在继承时的覆盖和隐藏规则
1.父类的实例变量和静态变量能被子类的同名变量隐藏
2.父类的静态方法被子类的同名静态方法隐藏
3.父类的实例方法被子类的同名实例变量覆盖
作为通用的规则:覆盖实例方法时,新方法的访问控制不能比原来的方法更严格,但可以更松。
1.在超类中被声明为公有的实例方法,在子类中也必须是公有的;
2.在超类中被声明为保护的实例方法,在子类中可以是保护的或公有的,但不能私有的。
3.在超类中默认的实例方法,在子类中其访问控制可以更严格。
4.在超类中被声明为私有的实例方法根本不能继承,也不能被覆盖。
子类覆盖父类的实例方法,必须有同样的(参数列表、参数名、参数返回类型),否则编译不能通过。
子类覆盖父类的实例方法,在jdk1.5后,参数返回类可以是父类方法返回类的子类
子类的静态方法不能隐藏同名的父类实例方法
java与C++一样,继承的方法具有多态性
还有几点需要注意的是
1、不能用子类的静态方法隐藏 父类中同样标示(也就是返回值 名字 参数都一样)的实例方法
2、不能用子类的实例方法覆盖 父类中同样标示的静态方法
3、变量只会被隐藏 不会被覆盖 ,无论他是实例变量还是静态变量,而且,子类的静态变量可以隐藏 父类的实例变量,子类的实例变量可以隐藏 父类的静态变量
4、最终方法(带关键字final的方法)不能被覆盖。
O(∩_∩)O哈哈~ 是不是有点儿绕口,没关系 我们看一个实例
创建两个父子类关系的类
- //父类
- class Parent
- {
- public static String kind="javastudy.extendsstudy.parent";
- public static int age=50;
- public String name="Parent";
- //静态方法,返回包名
- public static String getKind()
- {
- System.out.println("parent的getKind()方法被调用了");
- return kind;
- }
- //静态方法,返回年龄
- public static int getAge()
- {
- System.out.println("Parent的getAge()方法被调用了");
- return age;
- }
- //实例方法,返回姓名
- public String getName()
- {
- System.out.println("Parent的getName()方法被调用了");
- return this.name;
- }
- }
- //子类
- class Child extends Parent
- {
- public static String kind="javastudy.extendsstudy.child";
- public int age=25;
- public String name="child";
- //隐藏父类静态方法
- public static String getKind()
- {
- System.out.println("child的getkind()方法被调用了");
- return kind;
- }
- //获取父类包名
- public static String getParentKind()
- {
- return Parent.kind;
- }
- //覆盖父类实例方法
- public String getName()
- {
- System.out.println("child的getName()被调用了");
- return this.name;
- }
- //获取父类名称
- public String getParentName()
- {
- return super.name;
- }
- /*
- *错误,实例方法不能覆盖父类的静态方法
- public int getAge()
- {
- return this.age;
- }
- */
- }
然后测试下
- class Test
- {
- public static void main(String[] args)
- {
- Child child=new Child();
- System.out.printf("子类名称:%s,年龄:%d,包名:%s%n",child.name,child.age,child.kind);
- //输出:子类名称:child,年龄:25,包:javastudy.extendsstudy.child
- //把child转换成parent对象
- Parent parent=child;
- System.out.printf("转换后的名称:%s,年龄:%d,包名:%s%n",parent.name,parent.age,parent.kind);
- //输出:转换后的名称:Parent,年龄:50,包:javastudy.extendsstudy.parent
- System.out.printf("子类访问父类被隐藏的实例变量name:%s%n",child.getParentName());
- //输出:子类访问父类被隐藏的实例变量name:Parent
- System.out.printf("子类访问父类被隐藏的静态变量kind:%s",child.getParentKind());
- //输出:子类访问父类被隐藏的静态变量kind:javastudy.extendsstudy.parent
- child.getName();
- //输出:child的getName()被调用了
- //**************注意看这个方法,返回的还是子类的getName
- parent.getName();
- //输出:child的getName()被调用了
- child.getKind();
- //输出:child的getkind()方法被调用了
- parent.getKind();
- //输出:parent的getKind()方法被调用了
- }
- }
好了,看了结果后总结下吧
1.同名的实例方法被覆盖 ,同名的静态方法被隐藏 ,child类的getName实例方法覆盖 了parent的getName实例方法,chind的getKind方法隐藏 了parent类的getKind方法
2.隐藏 和覆盖 的区别在于,子类对象转换成父类对象后,能够访问父类被隐藏 的变量和方法,而不能访问父类被覆盖 的方法
3.如果需要访问父类被隐藏 的实例变量,加上super就好了,比如访问父类的name,写上super.name就好了
4.子类若要访问父类种被隐藏的类变量,则需要父类的名字加“.”来访问。比如:parent.name
本文不是教会大家重写父类变量的,而是重点说明方法和变量的隐藏和覆盖,这些个小知识点虽然在做项目的时候不怎么会用到,但是一定要记住,不然的话很多错误会感到莫名其妙,还有就是SCJP的题库里这类题大大存在,所以本人觉得这些细小的知识还是记住为好。
JAVA中方法和变量在继承中的覆盖和隐藏(一)的更多相关文章
- JAVA中方法和变量在继承中的覆盖和隐藏
出处:http://renyanwei.iteye.com/blog/258304 我们知道,在JAVA中,子类可以继承父类,如果子类声明的方法与父类有重名的情况怎么办,大伙儿都知道要是重写,但是实际 ...
- Java基础 成员变量的继承与覆盖
通过继承可以得到父类的成员变量,子类的成员变量包括从父类继承的成员变量(包括从祖先类中继承的成员变量)以及子类中重新定义的成员变量.本次介绍内容包括:可以继承哪些成员?如果子类和父类出现了相同的成员变 ...
- Java中的覆盖和隐藏以及final关键字
Java覆盖和隐藏 (1) 变量只能被隐藏(包括静态和非静态),不能被覆盖: (2) 可以用子类的静态变量隐藏父类的静态变量,也可以用子类的非静态变量隐藏父类的静态变量,也可以用非最终变量(final ...
- C++中的覆盖与隐藏(详细讲解)
C++类中覆盖与隐藏一直是一个容易理解出错的地方,接下来我就详细讲解一下区别在何处 覆盖指的是子类覆盖父类函数(被覆盖),特征是: 1.分别位于子类和父类中 2.函数名字与参数都相同 3.父类的函数是 ...
- Java中方法和类的深入分析
1.构造方法不能被继承.也就是说子类里没有父类的构造方法. Java重载根据的是实参和方法形参之间的匹配.自动类型转换也在重载版本的判断中起到了作用.重载的价值在于允许使用通用名称访问相关的方法. ...
- [Java学习]面向对象-类的继承;方法覆盖
一.类的继承 实现方法: public Class SubClass extends SuperClass{ } 继承最基本作用: 代码重用. 继承最重要的作用: 方法可以重写. 关于类的继承: 子类 ...
- Java基础语法Day_08(继承、抽象)
第1节 继承 day09_01_继承的概述 day09_02_继承的格式 day09_03_继承中成员变量的访问特点 day09_04_区分子类方法中重名的三种变量 day09_05_继承中成员方法的 ...
- C++中的重载、覆盖、隐藏
前几天面试时被问及C++中的覆盖.隐藏,概念基本答不上来,只答了怎么用指针实现多态,也还有遗漏.最终不欢而散.回来后在网上查找学习了一番,做了这个总结.其中部分文字借用了别人的博客,望不要见怪.引用的 ...
- [Java] 继承中,父类被覆盖的成员变量、方法的可访问性
在 Java 的继承机制里,在子类内部,可以访问父类被覆盖的变量和方法:在子类外部,可以访问父类的被覆盖变量,但是不能访问父类的被覆盖方法. 父类中被覆盖的方法不能在外部被方法,这是出于封装的考虑. ...
随机推荐
- git 撤销
在add之前撤回文件: git checkout src/com/jay/example/testforgit/MainActivity.java 已经add的,先取消添加,再撤回 git reset ...
- 使用 Git Hook 自动部署 Hexo 到个人 VPS
安装 Hexo 既然我的标题都已经那样写了,当然这个小节就不是本篇文章的重点了. 关于 Hexo 的安装跟配置,其实网上已经有很多很多文章了,随便一搜一大把.这里就有一篇超详细的,大家可以参考一下. ...
- Eclipse 常用快捷键和使用技巧
1.查看快捷键定义的地方 Window->Preferences->General->Keys. 2.更改启动页 在AndroidManifest.xml第一个activity标签项 ...
- java--Quartz 定时执行
第一步:引包(Maven) <!-- 定时任务 --> <dependency> <groupId>org.quartz-scheduler</groupId ...
- 在页面和请求中分别使用XML Publisher生成PDF报表且自动上传至附件服务器
两个技术要点: 1.使用TemplateHelper.processTemplate方法生成目标PDF的InputStream流,再使用ftp中上传流的方法将其上传至附件服务器. 2.在请求中调用AM ...
- 331. Verify Preorder Serialization of a Binary Tree -- 判断是否为合法的先序序列
One way to serialize a binary tree is to use pre-order traversal. When we encounter a non-null node, ...
- LINUX 操作记录到syslog,并发送到syslog服务器上
首先配置命令记录到syslog中: 在客户端的/etc/bashrc 下添加: logger -p local3.info \"`who am i` ================== ...
- 【转】HTTP协议—— 简单认识TCP/IP协议
转自:www.cnblogs.com/roverliang/p/5176456.html 大学没读计算机专业,所以很多的专业知识都不知道.既然已经从事了IT这个行业,就势必要去了解下网络底层,虽然实际 ...
- 【javascript基础】之【__lookupSetter__ 跟 __lookupSetter__】
描述: 返回getter setter所定义的函数 语法: obj.__lookupGetter__(sprop) 参数: getter setter中定义的字符串属性 注意:这不是标准的方法,ecm ...
- Maven入门-1.介绍及搭建开发环境
1.介绍1.1 Maven和Ant的比较?2.搭建Maven开发环境2.1 配置环境变量2.2 测试安装是否成功2.3 配置Maven的本地仓库位置3.Maven的约定4.Maven项目类型5.Mav ...