摘要

面向对象三大特性之一——继承

正文

继承

在继承的关系中,子类就是父类。也就是说,子类可以被当做父类来对待。

定义父类的格式:

text
1
2
3
4
5
public class 父类名称 {

//...

}

定义子类的格式:

text
1
2
3
4
5
public class 子类名称 extends 父类名称 {

//...

}

在父子类的继承中,如果成员变量重名,则创建子类对象时,访问有两种方式:

  1. 直接通过子类对象访问成员变量: 等号左边是谁,就优先用谁,没有则向上找;
  2. 间接通过成员方法访问成员变量: 该方法属于谁,就优先用谁,没有则向上找。
text
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
class Fu {
	int num=100;
	public void methodFu() {
		System.out.println(num);
	}
}
class Zi extends Fu {
	int num=200;
	public void methodZi() {
		System.out.println(num);
	}
}
public class Demo02ExtendsField {
	public static void main(String[] args) {
		Fu fu=new Fu();
		Zi zi=new Zi();
		
		System.out.println(zi.num);//200
		
		zi.methodZi();//200;
		zi.methodFu();//100;
	}
}

继承中的方法重写

局部变量:直接输出

本类的成员变量:this

父类的成员变量:super


方法重写 概念:在继承关系当中,方法的名称一样,参数列表也一样。

重写(Override):方法的名称一样,参数列表也一样。覆盖。[发生在继承关系当中]

重载(Overload):方法的名称一样,参数列表不一样。

方法覆盖的特点 创建的是子类对象,则优先使用子类方法

text
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
class Fu1 {
	int num=10;
	public void methodC() {
		System.out.println("父类重名方法执行");
	}
}
class Zi1 extends Fu1 {
	int num=20;
	public void method() {
		int num=30;
		System.out.println(num);//30 局部变量
		System.out.println(this.num);//20 该类中的成员变量
		System.out.println(super.num);//10 父类中的成员变量
	}
	public void methodC() {
		System.out.println("子类重名方法执行");
	}
}
public class Demo03ExtendsField {
	public static void main(String[] args) {
		Zi1 zi=new Zi1();
		zi.method();
		zi.methodC();
	}
	
}

方法重写的注意事项

  1. 必须保证父子类之间的方法的名称相同,参数列表也相同 @Override:写在方法前面,用来检测是不是有效地正确覆盖重写;这个注解只要不写,只要满足要求,也是正确的方法覆盖重写

  2. 子类方法的返回值必须小于等于父类方法的返回值范围 前提:Object类是所有类的公共最高父类(祖宗类),java.lang.String就是Object的子类;Object是最大的范围,String是他的子类,范围要小。

    text
     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    
    class Fulei {
    	public Object method() {
    		return null;
    	}
    }
    class Zilei extends Fulei {
    	@Override
    	public String method() {
    		return null;
    	}
    }
  3. 子类方法的权限修饰符必须大于等于父类方法的权限修饰符 提示:public>protected>(default)>private 备注:default不是关键字,是不写的情况下

    text
     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    
    class Fulei {
    	void method() {//这个默认是default
    
    	}
    }
    class Zilei extends Fulei {
    	@Override
    	public void method() {//public
    
    	}
    }

方法重写实际案例

text
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
class Phone {
	public void call() {
		System.out.println("打电话");
	}
	public void send() {
		System.out.println("发短信");
	}
	public void show() {
		System.out.println("显示号码");
	}
}
class NewPhone extends Phone {
	@Override
	public void show() {
		// TODO Auto-generated method stub
		super.show();
		System.out.println("显示姓名");
		System.out.println("显示头像");
	}
}
public class Demo05Phone {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		Phone p=new Phone();
		p.call();
		p.send();
		p.show();
		
		NewPhone np=new NewPhone();
		np.call();
		np.send();
		np.show();
	}

}

super关键字

继承关系中,父子类构造方法的访问特点:

  • 1.子类构造方法当中有一个默认隐藏的super()调用。所以一定是先调用父类构造方法,后调用子类构造方法

  • 2.子类构造可以通过super调用父类重载构造

  • 3.super的父类构造调用,必须是子类构造方法的第一个语句(第一个super的语句);

  • 总结:

    子类必须调用父类的构造方法,不写则赠送super();写了,则用指定的super(),super只能是第一个。

总结:

  • super关键字的用法有三种:
  • 1.在子类的成员方法中,访问父类的成员变量
  • 2.在子类的成员方法中,访问父类的成员方法
  • 3.在子类的构造方法中,访问父类的构造方法
text
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
class F {
	public F() {
		System.out.println("父类无参构造方法");
	}
	public F(int num) {
		System.out.println("父类有参构造方法");
	}
}
class Z extends F {
	public Z() {
		//super();默认有个隐藏的super();
		super(20);
		System.out.println("子类构造方法");
	}
	public void method() {
		//super();//此处会报错。只有子类构造方法,才能调用父类构造方法。
	}
}
public class Demo06Constructor {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		Z z=new Z();
	}

}

this关键字

super关键字用来访问父类内容,而this关键字用来访问本类内容。

三种用法:

  1. 在本类的成员方法中,访问本类的成员变量
  2. 在本类的成员方法中,访问本类的另一个成员方法
  3. 在本类的构造方法中,访问本类的另一个构造方法
    1. this调用跟super调用一样,也必须是构造方法的第一个语句,也必须是唯一一个
    2. super跟this都必须是第一个,并且两者不能同时使用
text
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
class 父 {
	int num=30;
}
class 子 extends 父 {
	int num=20;
	public void method(){
		int num=10;
		System.out.println(num);//10
		System.out.println(this.num);//20
		System.out.println(super.num);//30
	}
	
	public void methodA() {
		System.out.println("A");
	}
	public void methodB() {
		this.methodA();//A
		System.out.println("B");//B
	}
}