一个Java的小问题
老师今天在讨论群里抛出了一个问题,让大家尝试思考一下他所给的一段代码输出是什么。
其代码如下:
class T {
void foo() { this.bar(); }
void bar() { System.out.println("T.bar"); }
public static void main(String args[]) {
B b = new B();
b.foo();
}
} class B extends T {
void foo() { super.foo(); }
void bar() { System.out.println("B.bar"); }
}
思考了一波:
实例化子类对象,子类父类都没有显式构造器,就是在子类父类方法之间跳来跳去的。
“嗯,答案一定是'T.bar'”。
但还是敲了一遍,发现答案竟然是'B.bar'......(如图)
室友说:“对啊,this不就是指向当前对象嘛...”
(啪,打脸...疼...)
重新审视了一遍,才发现自己对于this还是没理解到位...
也就是说,整段代码执行流程如图:
问题就在于this.bar()的指向问题... 平时一般遇到this一般都会在本类里(这里就是T类)去找是否有将之实现的方法,若有,就是它了。
但是这次不同,事实上,正是this,使得当前方法指向其具体的对象,当这个对象实现了这个方法(这里的B类里将bar()方法覆盖了),自然this.bar()就会指向子类实现的这个bar()方法。
本质上,输出B.bar是方法覆盖的问题,但自己犯错的原因是this的指向问题。
因此,当我们稍微改一下代码。
将B类的bar方法注释掉,让其不能覆盖其父类T的bar方法,结果this依旧是指向B类对象,但要调用bar方法时,发现B类没有bar方法的实现,因此“追溯”到B的父类中去寻找bar方法,此时找到了父类的bar方法并将其调用,输出自然也就是T.bar(如图)。
此时,再来看另一种改动:只是在父类T中删掉了this,运行结果如图:
可以看到,程序的输出结果依旧是B.bar。(这或多或少超出了我的预料)
也就是说,这时的程序,和含有this关键字时,是一样的......
这道题给我的印象还是很深刻的,毕竟自己看完题之后,竟然一点儿都不谦虚地直接喊出了一个错误答案...
以后一定会多多注意this和super这样的很容易“改变”程序流程的关键字...
一个Java的小问题的更多相关文章
- 第一个java的小东西
第一次自己写的一个java的小东西,毕竟自己第一次写的,其中可谓是历经艰难,最后总结下来就是java实在是不适合写界面化的东西代码量比较大,这还不是最关键的,最关键的是控件的位置实在是太难控制了. 这 ...
- 一个Java线程小例子(仿火车票售卖)
public class MyThread extends Thread{ private static int ticket=100; public void run(){ for(int i=0; ...
- 福利贴——爬取美女图片的Java爬虫小程序代码
自己做的一个Java爬虫小程序 废话不多说.先上图. 目录命名是用标签缩写,假设大家看得不顺眼能够等完成下载后手动改一下,比方像有强迫症的我一样... 这是挂了一个晚上下载的总大小,只是还有非常多由于 ...
- Java学习笔记二十九:一个Java面向对象的小练习
一个Java面向对象的小练习 一:项目需求与解决思路: 学习了这么长时间的面向对象,我们只是对面向对象有了一个简单的认识,我们现在来做一个小练习,这个例子可以使大家更好的掌握面向对象的特性: 1.人类 ...
- webmagic的设计机制及原理-如何开发一个Java爬虫
之前就有网友在博客里留言,觉得webmagic的实现比较有意思,想要借此研究一下爬虫.最近终于集中精力,花了三天时间,终于写完了这篇文章.之前垂直爬虫写了一年多,webmagic框架写了一个多月,这方 ...
- 【JMeter】JMeter完成一个java请求的压测
先定义一下我说的remoteService:即远程调用服务,没有http的url.不对外提供或者对外提供有限的服务.具体视各公司的代码架构所定,比如有些公司为web工程,scf服务,db.scf即为服 ...
- 做为一个Java程序员,你需要哪些傍身的技能?
最近总有些断断续续的思考,想想从我入行以来,我到底学会了什么,做成过什么,以后要做什么,如何提升自己······· 工作3年了,常听人说3年,5年,10年是程序员的坎,每过一个都会有新的想法,新的改变 ...
- 师兄写的一个JAVA播放器的源代码(转)
师兄写的一个JAVA播放器的源代码 MediaPlayer.java------------------------------------------------------------------ ...
- Java开发小技巧(三):Maven多工程依赖项目
前言 本篇文章基于Java开发小技巧(二):自定义Maven依赖中创建的父工程project-monitor实现,运用我们自定义的依赖包进行多工程依赖项目的开发. 下面以多可执行Jar包项目的开发为例 ...
随机推荐
- Codeforces 1313C.Skyscrapers
题目链接 题意是给你一个数组,问你如何建造,使得每个点都不小于其左右的点,包括不相邻的点 分析题意,容易得知,就是找一个点两侧的不上升序列且带修,那我们就分别从头跑一遍,从尾跑一遍,两者相加就是每个点 ...
- 最长公共子序列-Hdu1159
Common Subsequence Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Other ...
- 带有“全选”的combotree
<div id="setBtn_dd" class="easyui-window" data-options="iconCls:'icon-sa ...
- 服务器(2)——IIS(2)——IIS Express(1)——IIS跟IIS Express之间的区别和关系
在早期开发.NET WEB应用的时候,是需要为应用项目配置一个IIS下的虚拟应用(VS会自动配置,也可以手工指定),但这个要求操作系统必须支持IIS并且安装IIS(WINDOWS 7 HOME版本是不 ...
- 吴裕雄 python 神经网络——TensorFlow 实现LeNet-5模型处理MNIST手写数据集
import os import numpy as np import tensorflow as tf from tensorflow.examples.tutorials.mnist import ...
- docker+hexo 搭建博客
前提 Linux服务器 保证自己服务器上的端口对外开放,即设置相应的防火墙规则 安装好hexo 安装:npm install hexo-cli -g 初始化搭建:npm init myBlog,myB ...
- 九、web.xml理解
1.web.xml文件在每个web工程不是必须要有的: web.xml文件是用来初始化配置信息:比如Welcome页面.servlet.servlet-mapping.filter.liste ...
- python--脚本传参与shell脚本传参(位置参数)
写一个最简单的shell脚本,了解shell脚本是如何传参 1. vim test1.sh name=$1 age=$2 echo ${name} echo ${age} 2.调用脚本并传参 sh t ...
- Chrome 打不开任意网页以及设置、扩展程序等页面解决方法
解决办法:在快捷键加启动参数 -no-sandbox,如果可以启动,就说明是电脑上有某个软件与Chrome沙盒有冲突
- 入门项目数字手写体识别:使用Keras完成CNN模型搭建(重要)
摘要: 本文是通过Keras实现深度学习入门项目——数字手写体识别,整个流程介绍比较详细,适合初学者上手实践. 对于图像分类任务而言,卷积神经网络(CNN)是目前最优的网络结构,没有之一.在面部识别. ...