java 面向对象1之继承

------------恢复内容开始------------

首先是需要创建的类,统一创建在oopTest包下:

 

student类为父类,smallStudent类与bigStudent类继续student类。

student类的代码如下,其中有姓名和成绩两个属性并带有一个显示的方法

 1 package oopTest;
 2 
 3 public class Student {
 4     String name;
 5     double score;
 6     public String getName() {
 7         return name;
 8     }
 9     public void setName(String name) {
10         this.name = name;
11     }
12     public double getScore() {
13         return score;
14     }
15     public void setScore(double score) {
16         this.score = score;
17     }
18     public void showScore() {
19         System.out.println("姓名为:" + name + "\t成绩为:" + score);
20     }
21 }

smallStudent类的代码如下,自带的方法为music(),唱跳.....

1 package oopTest;
2 
3 public class smallStudent extends Student{
4     public void music() {
5         System.out.println("小学生会音乐");
6     }
7 }

bigStudent类的代码如下,自带的方法为reading(),疯狂阅读...

1 package oopTest;
2 
3 public class bigStudent  extends Student{
4     public void reading() {
5         System.out.println("大学生会阅读");
6     }
7 }

最后需要一个测试类来测试子类继续的属性与方法,代码如下

 1 package oopTest;
 2 
 3 public class TestExtendsMain {
 4     public static void main(String[] args) {
 5         smallStudent smalls = new smallStudent();
 6         smalls.setName("小学生");
 7         smalls.setScore(90);
 8         smalls.music();
 9         smalls.showScore();
10         
11         bigStudent bigs = new bigStudent();
12         bigs.setName("大学生");
13         bigs.setScore(100);
14         bigs.reading();
15         bigs.showScore();
16     }
17 }

运行结果和预料的一样,这是最基本的类继承的常识,不多说(下面开始剖析this(),super()还有构造方法与继承的关系

 1 package oopTest;
 2 
 3 public class TestExtendsMain {
 4     public static void main(String[] args) {
 5         smallStudent smalls = new smallStudent();
 6         smalls.setName("小学生");
 7         smalls.setScore(90);
 8         smalls.music();
 9         smalls.showScore();
10         
11         bigStudent bigs = new bigStudent();
12         bigs.setName("大学生");
13         bigs.setScore(100);
14         bigs.reading();
15         bigs.showScore();
16     }
17 }

先贴上上面代码的继承关系图

 

开始今天的重点,this(),super()

this(),测试的代码如下,初始化子类smallStudent

1 package oopTest;
2 
3 public class TestExtendsMain {
4     public static void main(String[] args) {
5         smallStudent smalls = new smallStudent();
6     }
7 }

为父类student添加一个无参构造方法并显示出来

 

 1 package oopTest;
 2 
 3 public class Student {
 4     String name;
 5     double score;
 6     public String getName() {
 7         return name;
 8     }
 9     public void setName(String name) {
10         this.name = name;
11     }
12     public double getScore() {
13         return score;
14     }
15     public void setScore(double score) {
16         this.score = score;
17     }
18     public void showScore() {
19         System.out.println("姓名为:" + name + "\t成绩为:" + score);
20     }
21     public Student() {
22         System.out.println("调用父类的无参构造方法");
23     }
24 }

 

为子类smallstudent分别添加一个无参构造方法和有参构造方法,并在无参构造方法中使用this()调用有参构造方法

 1 package oopTest;
 2 
 3 public class smallStudent extends Student{
 4     public void music() {
 5         System.out.println("小学生会音乐");
 6     }
 7     public smallStudent() {
 8         this("jump");
 9         System.out.println("子类的无参构造方法");
10     }
11     public smallStudent(String behavior) {
12         System.out.println("子类的有参构造方法");
13     }
14 }

看看结果,可以知道子类的构造方法在初始化时会先调用父类的无参构造方法,而this()可以通过输入的参数调用本类相应的构造方法

 

 

注意:this()与super()调用的构造方法必须存在且在构造方法的最顶层否则会报错,如下初始化错误

 

看看super()方法,依旧是通过初始化一个子类的方式来看

1 package oopTest;
2 
3 public class TestExtendsMain {
4     public static void main(String[] args) {
5         smallStudent smalls = new smallStudent();
6     }
7 }

父类依旧

 

 1 package oopTest;
 2 
 3 public class Student {
 4     String name;
 5     double score;
 6     public String getName() {
 7         return name;
 8     }
 9     public void setName(String name) {
10         this.name = name;
11     }
12     public double getScore() {
13         return score;
14     }
15     public void setScore(double score) {
16         this.score = score;
17     }
18     public void showScore() {
19         System.out.println("姓名为:" + name + "\t成绩为:" + score);
20     }
21     public Student() {
22         System.out.println("调用父类的无参构造方法");
23     }
24 }

 

将子类的this()方法改为super()

 1 package oopTest;
 2 
 3 public class smallStudent extends Student{
 4     public void music() {
 5         System.out.println("小学生会音乐");
 6     }
 7     public smallStudent() {
 8         super();
 9         System.out.println("子类的无参构造方法");
10     }
11     public smallStudent(String behavior) {
12         System.out.println("子类的有参构造方法");
13     }
14 }

运行结果如下,说明子类的构造器在初始化时会在顶层默认调用super()方法

 

 

以下代码使用子类的有参构造方法进行初始化,并没有写下super(),结果依然调用了父类的无参构造方法

1 package oopTest;
2 
3 public class TestExtendsMain {
4     public static void main(String[] args) {
5         smallStudent smalls = new smallStudent("jump");
6     }
7 }
 1 package oopTest;
 2 
 3 public class smallStudent extends Student{
 4     public void music() {
 5         System.out.println("小学生会音乐");
 6     }
 7     public smallStudent() {
 8         System.out.println("子类的无参构造方法");
 9     }
10     public smallStudent(String behavior) {
11         System.out.println("子类的有参构造方法");
12     }
13 }

-----------------------------------------------------------------------------------------------------------------------------------------------------------------------

接下来创建三个类,a,b,c类,a继承b类,b类继承c类

 以下为a类的代码,只有一个无参构造方法

1 package oopTest;
2 
3 public class a {
4     public a() {
5         System.out.println("我是a类的无参构造方法");
6     }
7 }

以下为b类的代码,提供一个无参的构造方法

1 package oopTest;
2 
3 public class b extends a{
4     public b() {
5         System.out.println("调用了b类的无参构造方法");
6     }
7 }

以下为c类的代码,提供一个无参与有参的构造方法

 1 package oopTest;
 2 
 3 public class c extends b{
 4     public c() {
 5         this("string");
 6         System.out.println("调用了c类的无参构造方法");
 7     }
 8     public c(String args) {
 9         System.out.println("调用类c类的有参构造方法");
10     }
11 }

测试代码,初始化一个c类

1 package oopTest;
2 
3 public class TestExtendsMain {
4     public static void main(String[] args) {
5         c c1 = new c();
6     }
7 }

可以推测一下结果,首先初始化c类的构造器,但是因为c类继承类b类,所以先初始化b类的构造器,以此类推,a类的无参构造方法--》b类的无参构造方法--》c类的有参构造方法--》c类的无参构造方法

运行结果为

可以发现结果是调用了c类的父类b类与它的父类a类的“一个”构造方法,当然它也只有一个构造方法于是给a类和b类写上一个有参的构造方法,看看会不会在初始化时调用父类的两个构造方法

代码如下,分别在a类和b类创建了有参的构造方法

 1 package oopTest;
 2 
 3 public class a {
 4     public a() {
 5         System.out.println("我是a类的无参构造方法");
 6     }
 7     public a(String args) {
 8         System.out.println("我是a类的有参构造方法");
 9     }
10 }
 1 package oopTest;
 2 
 3 public class b extends a{
 4     public b() {
 5         System.out.println("调用了b类的无参构造方法");
 6     }
 7     public b(String args) {
 8         System.out.println("调用类b类的有参构造方法");
 9     }
10 }

在c类的无参构造方法中使用super(),结果如下

 1 package oopTest;
 2 
 3 public class c extends b{
 4     public c() {
 5         super();
 6         System.out.println("调用了c类的无参构造方法");
 7     }
 8     public c(String args) {
 9         System.out.println("调用类c类的有参构造方法");
10     }
11 }

 如果给c类的super()加上参数会怎么样?

 1 package oopTest;
 2 
 3 public class c extends b{
 4     public c() {
 5         super("string");
 6         System.out.println("调用了c类的无参构造方法");
 7     }
 8     public c(String args) {
 9         System.out.println("调用类c类的有参构造方法");
10     }
11 }

通过结果可以看到,c类的super(string)调用了父类b类的“一个”有参构造方法,证明父类只会调用一个构造方法?

我们试试以下这段代码

 1 package oopTest;
 2 
 3 public class c extends b{
 4     public c() {
 5         this("string");
 6         System.out.println("调用了c类的无参构造方法");
 7     }
 8     public c(String args) {
 9         super("string");
10         System.out.println("调用类c类的有参构造方法");
11     }
12 }

通过初始化c类的无参构造方法,运行的顺序为 a类的无参构造方法--》b类的无参构造方法--》c类的有参构造方法--》b类的有参构造方法--》c类的有参构造方法

结果为

 

 

从上面的运行顺序来看,b类的无参构造方法确实调用了(临时),但是在之后它被b类的有参构造方法顶替了,而a类即使有两个构造方法也没有被顶替掉,由此可见,父类的构造器在初始化时只会把最后调用的一个构造器显示出来。

最后,我们如果在b类的有参构造方法中使用super()调用a类的有参构造方法是否也会这样呢?

 1 package oopTest;
 2 
 3 public class b extends a{
 4     public b() {
 5         System.out.println("调用了b类的无参构造方法");
 6     }
 7     public b(String args) {
 8         super("string");
 9         System.out.println("调用类b类的有参构造方法");
10     }
11 }

结果是肯定的,a类的无参构造方法被销毁了(也许是被重载了这部分我也有点迷),谢谢耐心观看本篇文章的小伙伴们,下一篇,封装!!

posted @ 2020-07-05 02:05  zemengchen  阅读(52)  评论(0编辑  收藏  举报