参考链接: 可以重写Java中的私有方法吗

JAVA面向对象之代码块与继承

代码块分类

局部代码块

作用:限制变量生命周期

书写位置:在方法中

构造代码块

开发中很少使用

书写位置:类中  方法外

调用时机:如果你有构造代码块 系统会帮你调用 帮你在创建对象时调用

静态代码块(一定是被static修饰)

依赖类 随着类的加载而加载

注意:只加载一次(系统只创建一次 不管你调用多少对象)

应用场景:U盘装载驱动程序(第二次插入U盘,不会再加载驱动程序)

加载驱动(数据库驱动 JDBC)

同步代码块(多线程)

这里暂时不做介绍 后续给予说明

代码示例

public class Demo24 {

//第三代码块

{

int a = 10;

System.out.println(a);

System.out.println("我是Demo24构造代码块");

}

public static void main(String[] args){

Person2 person = new Person2();

person.name = "张三";

person.age = 15;

person.sayHi();

System.out.println("我是main函数中得普通方法");

{

System.out.println("我是局部代码块");

}

Person2 person1 = new Person2("李四",22);

}

}

class Person2{

String name;

int age;

//第一个代码块

static {

System.out.println("我是person类的静态代码块");

}

//第二个代码块

{

//每一个对象 都会调用同一个方法 这时可以使用

sleep();

System.out.println("我是构造代码块");

}

public Person2(){

System.out.println("我是无参数的构造方法");

}

public Person2(String name, int age){

this.name = name;

this.age = age;

System.out.println("我是有参数的构造方法");

}

public String getName(){

return name;

}

public void setName(){

this.name = name;

}

public int getAge(){

return age;

}

public void setAge(int age){

this.age = age;

}

public void sayHi(){

System.out.println("姓名:" + name + "年龄:" + age);

}

public void sleep(){

System.out.println("睡觉");

}

}

运行结果

我是person类的静态代码块

睡觉

我是构造代码块

我是无参数的构造方法

姓名:张三年龄:15

我是main函数中得普通方法

我是局部代码块

睡觉

我是构造代码块

我是有参数的构造方法

姓名:李四年龄:22

解释

当程序运行时 会先加载Demo01.class文件,进入.class文件后,会寻找静态代码块,如果没有,会继续寻找构造代码块,由于没有

Demo24类的实例对象,所有构造代码块与构造方法均不会执行,如果另外新建一个类,Demo25,在Demo25类中建立Demo24类的实例

对象,Demo24类中的构造代码块与构造方法便会执行,之后会首先寻找main函数,找到main函数后,(局部代码块定义在方法中,在该

方法中并没有优先级)会首先遇到Person2类,遇到Person2 person = new Person2();这时会加载Person2类,

加载Person2.class文件,静态代码块与静态方法和静态属性一样,会随着类的加载而加载,存放在方法区的静态区,与对象无关,所

以在加载Person2.class文件时,会将static代码块一同加载,所有会输出'我是Person类的静态代码块',之后需要new一个对象,

继续执行Person2类中的代码,执行时,会先寻找有没有构造代码块(构造代码块存放在类中方法外,优先级高于构造方法);发现有构

造代码块,即先执行构造代码块,构造代码块中有sleep方法,故先执行sleep方法,打印'睡觉',之后执行下一句,打印'我是构造代码

块',构造代码块执行之后,会执行相应的构造方法(有参或者无参),构造代码块优先于构造方法执行,与构造代码块的位置无关,new

对象的时候没有传递参数,所有这里调用无参构造方法,打印'我是无参数的构造方法',之后回到Demo01函数,对对象中的变量进行赋

值,赋完值后,调用对象的sayHi方法,打印'姓名:张三','年龄:15',随后执行到打印语句,打印出"我是main函数中得普通方法",

之后遇到局部代码块,打印"我是局部代码块"(顺序执行),当new第二个Person2对象时,静态代码块不会再执行,即在函数运行过

程中,只会加载一次,非静态构造代码块将会继续加载,第二次new对象时候,先执行构造代码块,构造代码块中有sleep方法,所有会

先执行sleep方法,打印"睡觉",随后打印"我是构造代码块",new对象时候,传进来了参数,所有会调用Person2类中的有参数构造

方法,打印"我是有参数的构造方法",赋值后,调用sayHi方法,打印"姓名:李四年龄22",函数运行结束.

继承

继承特点

1.减少你的代码量

2.让类与类之间产生关联(产生 父子的)

继承弊端

当父类中添加新德属性时候,比如白血病,子类即使不想继承这个属性,却还是由于

继承的关系,自动得到了白血病这个属性

注意

1.继承时  可把多个类中 相同的功能或方法 抽取出来 重新构造一个类出来

把这些类建立 继承关系

2.建立继承关系的同时 一定要符合逻辑(切记不要为了继承而继承)

3.继承使用关键字:extends

举例

继承:

手机类  <打电话 发短信 玩游戏>

苹果手机类 继承 手机类 <打电话 发短信 玩游戏 爆炸>

小米手机类 继承 手机类 <打电话 发短信 玩游戏 暖手功能>

项目经理:姓名 工资 工号 分红

程序员:姓名 工资 工号

项目经理 继承 程序员 就继承了姓名 工资 和 工号 ,特有功能 分红 这样不行

不符合逻辑

应该是相同的功能抽取出来

员工类 姓名 工资 工号

项目经理 和 程序员 继承员工类  这样才符合逻辑

注意

如果是继承关系 一定符合什么是什么

项目经理是员工 子类是父类的

动物 猫 狗 马

猫 是 动物 √

动物 是 猫 ×

水果(父类) 香蕉 苹果 橘子

水果 是 香蕉 ×

香蕉 是 水果 √

继承的写法

class 子类 extends 父类{

}

代码示例

/*

* 猫类

* 姓名 颜色  种类 会睡觉 会抓老鼠

* 狗类

* 姓名 颜色  种类 会睡觉 会啃骨头

*/

// 抽取出 相同部分 组成 动物类

public class Demo02{

public static void main(String[] args){

Cat cat = new Cat();

cat.name = "汤姆";

cat.color = "灰色";

cat.kind = "灰猫";

cat.sleep();

cat.sayHi();

}

}

class Animal{

String name;

String color;

String kind;

public void sleep(){

System.out.println("睡觉");

}

public void sayHi(){

System.out.println("姓名:" + name +"颜色:" + color + "种类:" + kind);

}

}

class Cat extends Animal{

public void hitMouse(){

System.out.println("抓老鼠");

}

}

class Dog extends Animal{

public void eatBone(){

System.out.println("啃骨头");

}

}

运行结果:

抓老鼠

睡觉

姓名:汤姆颜色:灰色种类:灰猫

JAVA中的继承

注意

1.java 只允许 单继承(多继承 可以 使用 接口 来间接实现)

2.java 中 允许 多层继承(爷爷 父亲 儿子 孙子 重孙子....)

java中 最顶层的父类(最基础类) Object类

如果我这个类没有写 继承哪个父亲 默认就是继承 Object类

1.如果我要使用 这些 类中 共有的方法(属性) 使用 哪个类?

创建当前继承中最 顶端的 类 去使用

2.如果我要使用 这些 类中 特有的方法(属性) 使用 哪个类?

创建当前继承中 最末端类 去使用

代码示例

public class Demo03 extends Object{

}

//A类 爷爷类 B类 是父亲 C类 是 孙子类

//A类中又name C类中 会叫爷爷

class A extends Object{

String name;

}

class B extends A{

}

class C extends B{

public void speak(){

System.out.println("会叫爷爷");

}

}

构造方法能不能被继承?

爷爷 父亲 儿子

爹 和 儿子 都用同一中 方法生出来 行吗? 乱

奶奶不愿意  妈妈不愿意

构造方法是不能被继承的

为了保证继承的完整性 在你创建对象的时候

如果你不调用 父类的构造方法

系统会帮你去调用 父类的无参构造方法

代码举例

public class Demo04{

public static void main(String[] args){

Son son = new Son();

son.name = "张三";

son.sayHi();

//有参构造对象

Son son2 = new Son("小明");

son2.sayHi();

}

}

class Father{

String name;

//有参 无参 构造方法

public Father(){

System.out.println("我是无参构造方法");

}

public Father(String name){

this.name = name;

System.out.println("我是有参构造方法");

}

public void sayHi(){

System.out.println("姓名:" + name);

}

}

class Son extends Father{

//无参构造

public Son(){

//如果你没有在子类的构造方法中 调用父类的构造方法

//系统会默认给你的子类构造方法中 添加一行代码

super();//调用父类的 无参构造方法

System.out.println("我是儿子类的无参构造方法");

}

//有参的

public Son(String name){

//如果你没有在子类的构造方法中 调用父类的构造方法

//系统 会默认 给你的子类 构造方法中 添加一行代码

super(); //系统帮你调用父类的构造方法

this.name = name;

System.out.println("我是儿子类的有参构造方法");

}

}

输出结果

我是爸爸类无参的构造方法

我是儿子类无参构造方法

张三

我是爸爸类无参的构造方法

我是儿子类有参的构造方法

小明

结果解释

当new一个Son对象时,由于没有传进去参数,所以会先调用儿子类的无参构造方法,

由于Son类是Father的子类,所有在子类的构造方法中会自动调用父类的无参构造方

法,从而实现Son类的实例对象同时具有Son类与Father类的属性与方法,因此先打印

父类无参构造方法中的"我是爸爸类的无参构造方法",之后返回子类构造方法,打印

子类无参构造器中得"我是儿子类无参构造方法",之后对Son的nane属性赋值,调用s

ayHi方法将姓名打出

第二次new一个Son类对象的时候,传进去姓名这个参数,所有会调用Son类中得有参

构造方法,该有参构造方法中第一句会先执行super(),即会先执行父类无参构造方

法,向上调用父类构造方法时,没有传进去参数,所有不会调用父类有参构造方法,打

印"我是爸爸类无参构造方法"后,返回子类,即Son类,打印"我是儿子类有参构造方

法",然后将姓名赋值,随后返回main函数,调用sayHi方法将name打印出来.

super关键字

super 用于指向子类对象中的父类对象(构造方法)  相当于父类的对象

super 调用对象 super.对象

super 调用方法 super.方法()

super(); 调用父类的构造方法

this();  调用的是本类的构造方法

代码示例

public class Demo05{

public static void main(String[] args){

TestB b = new TestB();

b.fun();

}

}

class TestA{

int num1 = 10;

int num2 = 20;

public void sayHi(){

System.out.println("我是父类的sayHi方法");

}

}

class TestB extends TestA{

int num1 = 30;

public void fun(){

//使用this时 会先在本类中寻找该属性

//没找到 就去父类中找  就近原则

System.out.println(this.num1);  //30

System.out.println(this.num2);  //20

System.out.println(this.num3);  //10

}

}

思考:如果父类中没有无参构造方法 咋整?

建议:不管是父类 还是 子类 构造方法一定要写全,避免出现问题

代码举例

public class Demo04{

}

class Phone{

String name;

public Phone(){

}

public Phone(String name){

this.name = name;

}

}

class MI extends Phone{

public MI(){

//子类的构造方法 如果你什么都不写 会默认调父类无参构造

//如果父类中 没有无参构造 就证明父类中一定有有参的构造方法

//父类构造方法无论有参 还是 无参, 子类的构造方法都必须要调用一个

//必须手动指定一个有参构造方法去调用

super("Note2");

}

public MI(String name){

super(name);

}

}

方法的重写

思考: 如果父类 和 子类的 方法 重名了,咋整?能不能重名?

答案是可以  方法的重写

注意

1.方法的声明完全一致的 叫方法的重写

2.方法的重写建立在类与类之间有继承关系(子类重写父类的方法)

Override(重写)和Overload(重载) 的区别

1.重写前提:需要继承关系

重载:在同一个类里面实现

2.重写:需要方法的声明完全一致

重载:相同的功能,不同的实现方式 只跟参数有关

代码示例

public class Demo07{

public static void main(String[] args){

IOS8 ios8 = new IOS8();

ios8.siri();

//如果直接打印对象 相当于 系统帮你打印时 调用 toString()方法

System.out.println(ios8);   //输出haha

System.out.println(ios8.toString());   //输出haha

}

}

class IOS7{

public void call(){

System.out.println("打电话");

}

public void siri(){

System.out.println("说英文");

}

}

class IOS8 extends IOS7{

//方法的重写:对父类的方法 进行一个功能上的升级

//调不调父类的方法 要根据实际情况

public void siri(){

//中 英文都会说

super.siri();   //调用父类的方法

System.out.println("会说中文");

}

//重写toString()方法

//利用toString方法 来写介绍自己的方法

public String toString(){

return "haha";

}

}

重写toString()方法介绍

toString方法是Object类中的一个方法,故所有继承Object类的类,这些类中都有toString方法;

假设有一个类为Animal,他的一个对象为animal,则System.out.println(animal),

打印出来的是一个全限定类名com.lanou3g.IOS7@33909752,而打印System.out.println(animal.toString),

.lanou3g.IOS7@33909752,即包名+类名+@33909752,说明打印animal与打印animal.toString()的结果是一样的,toString()方法写完整则是

public String toString(){},即说明toString方法是有返还值的,即打印animal.t

oString()的结果,打印的是toString()函数中return语句返还的值,而打印animal

的结果又与打印animal.toString()方法的值相同,说明打印对象名所得到的结果就

是toString中return语句返还的结果,所有重写Object类中得toString方法,改变re

turn语句的返还值,然后直接打印对象名,便可以得到自己想要的结果.具体结果如上面代码所示

实例练习继承关系

需求

老师类 学生类

* 无参 有参构造 set/get方法 成员变量私有化 介绍自己的方法

属性:姓名,年龄

* 行为:吃饭

* 老师有特有的方法:讲课

* 学生有特有的方法:学习

代码实现

package com.lanou3g;

public class Demo08 {

public static void main(String[] args) {

//创建一个学生

Student student = new Student("王龙",15,1);

System.out.println(student);

Teacher teacher = new Teacher("刘",13);

System.out.println(teacher);

}

}

class Person1{

//属性

//继承中private修饰的变量 是不能直接访问的 但可以间接访问的

private String name;

private int age;

//构造方法

public Person1() {

}

public Person1(String name, int age) {

this.name = name;

this.age = age;

}

//set/get方法

public String getName() {

return name;

}

public void setName(String name) {

this.name = name;

}

public int getAge() {

return age;

}

public void setAge(int age) {

this.age = age;

}

//特有方法

public void eat() {

System.out.println("吃饭");

}

//介绍自己的方法

@Override

public String toString() {

// TODO Auto-generated method stub

return "姓名:" + name + "年龄" + age;

}

}

//学生类

class Student extends Person1{

//学号

private int num;

public int getNum() {

return num;

}

public void setNum(int num) {

this.num = num;

}

//构造方法

public Student(){

}

//有参

public Student(String name, int age, int num) {

//直接调用父类的构造方法 完成赋值初始化

//为了保证继承的完整性 在子类构造方法中

//第一行 必须调用父类的构造方法(无参 有参都行)

super(name,age);

//特有属性 直接赋值就行

this.num = num;

}

public void study() {

System.out.println("学生在学习");

}

//介绍自己的方法

@Override

public String toString() {

//可以在父类的基础上 添加自己特有的属性 去打印

return super.toString() + "学号:" + num;

}

}

//教师类

class Teacher extends Person1 {

public Teacher(){

}

public Teacher(String name, int num) {

super(name,num);

}

public void teach() {

System.out.println("老师会讲课");

}

@Override

public String toString() {

// TODO Auto-generated method stub

return super.toString();

}

}

[转载] JAVA面向对象之代码块 继承 方法的重写 super关键字与重写toString()方法介绍相关推荐

  1. -1-2 java 面向对象基本概念 封装继承多态 变量 this super static 静态变量 匿名对象 值传递 初始化过程 代码块 final关键字 抽象类 接口

    java是纯粹的面向对象的语言 也就是万事万物皆是对象 程序是对象的集合,他们通过发送消息来相互通信 每个对象都有自己的由其他的对象所构建的存储,也就是对象可以包含对象 每个对象都有它的类型  也就是 ...

  2. Java面向对象与代码编写

    Java面向对象与代码编写 面向过程的思想和面向对象的思想 面向对象和面向过程的思想有着本质上的区别, 作为面向对象的思维来说,当你拿到一个问题时,你分析这个问题不再是第一步先做什么,第二步再做什么, ...

  3. Java中普通代码块,构造代码块,静态代码块区别

    Java中普通代码块,构造代码块,静态代码块区别及代码 示例 //执行顺序:(优先级从高到低.)静态代码块>mian方法 >构造代码块>构造方法. 其中静态代码块只执行一次.构造代码 ...

  4. java 面向对象三大特性之继承 万字详解(超详细)

    目录 前言 : 一.为什么需要继承: 二.什么是继承(Warning : 篇幅较长)? 1.继承概述: 2.子类继承父类之后达到的效果 : ①如何使用继承? ②代码演示 : 3.继承的使用场景: eg ...

  5. java中static代码块_static怎样在java中修改代码块?

    代码是我们每个学编程的小伙伴都接触的内容,在代码块的修改上有很多方法,那么在java中又需要使用哪种方式来对代码块进行变动呢?哦们最近在学关键字的版块,其中有一个static用来修饰代码块的效果非常不 ...

  6. Java面向对象三大特性之继承多态的预习笔记,are you ready? 面对疾风吧!

    文章目录 继承(extends) super关键字 方法重写 instanceof关键字 abstract关键字 接口(interface) 多态 继承(extends) AextendsB A继承了 ...

  7. 【零基础学Java】—finally代码块(四十七)

    [零基础学Java]-finally代码块(四十七)

  8. Java中static代码块,main函数,构造函数运行顺序

    1.Java中static代码块,main函数,构造函数运行顺序如下: 答:static代码块是主动执行的,因此static代码块先执行,然后是执行构造函数,最后是Main函数. 如下例子: publ ...

  9. java中构造代码块、方法调用顺序问题

    1. 继承的概念 继承在本职上是特殊--一般的关系,即常说的is-a关系.子类继承父类,表明子类是一种特殊的父类,并且具有父类所不具有的一些属性或方法. 2. 继承中的初始化顺序 从类的结构上而言,其 ...

最新文章

  1. 0基础玩转CV的利器绝了,还送万元礼金,机不可失!
  2. 用python画花瓣-Python:绘制樱花树
  3. 使用squid在阿里云服务器(centos7)上搭建自己的代理服务器
  4. 一个本地分支能关联两个远程仓库吗_使用git分支保存hexo博客源码到github
  5. 使用 Avalonia 开发 UOS 原生应用
  6. javascript嵌套函数和在函数内调用外部函数的区别
  7. java 将list按指定大小等分,最后多余的单独一份
  8. www.yaxjf.com+m.php,linux运维架构--PHP开发-零基础学习PHP视频教程
  9. php不兼容_怎么解决php不兼容问题
  10. latex textbf没有用_把知乎改造成LaTex创作平台
  11. linux fastboot 工具,fastboot工具(FastbootCommander)
  12. 手游和平精英透视教学
  13. vue-d2admin前端axio异步请求详情
  14. mumu模拟器切换android,MuMu模拟器“键位设置”功能详解!如有问题请联系在线客服~...
  15. Windows文件系统-NTFS文件系统
  16. 找到一个数组对象中 '某某某(属性名)'为 ['某某','某某']的值
  17. 【CVPR2020】Designing Network Design Spaces
  18. 轻便简洁的电脑录音软件,免费收藏!
  19. 2022-XTU程设练习1
  20. 低秩分解(张量分解)

热门文章

  1. SpringMVC那点事
  2. tiny4412移植tslib库
  3. 2.4一元多项式的表示及相加,含cpp算法
  4. twisted mysql_Twisted MySQL adbapi返回字典
  5. distinct返回null报错_C#之集合常用扩展方法与Linq
  6. java g1 gc ref proc_深入理解垃圾收集器的G1及日志分析
  7. html dom透明度,HTML DOM Style overflow 属性
  8. java选项设置_java环境配置
  9. 表字段顺序有何影响_「品味保定」炸烹虾段乾隆赞 百年保定柔雅香
  10. pb 怎么判断是 小数_考试90分以上的孩子是怎么学数学的?听听老师怎么说?