继承
有一个关键字可以建立父子关系
public class B extend A{
}
B继承A
子类可以直接继承父类的非私有成员(成员变量,成员内函数)
子类对象是由子类,父类共同完成的。
权限修饰符
上图ZI这个类是继承了Fu这个类所以可以访问到Fu中的protected(受保护类)和public(公开)
易错点在于protected是规定给子类访问的,不是规定给对象在别的类中访问的(规则)
单继承
java中只能单继承不能多继承,但是可以多层继承
为什么不支持多继承是因为 如果多个父类中有相同的成员函数,成员,就没办法分辨继承谁的
object类
是所有类的父类
重写
对父类中的方法进行重写(列表参数一样)覆盖父类的方法
public class B extends A{
// 方法重写
@Override // 安全,可读性好
public void print1(){
System.out.println("666");
}
// 方法重写
@Override
public void print2(int a, int b){
System.out.println("666666");
}
}在重写方法前面加上一个注解,可以指定java编译器,检查方法重写格式是否正确
@Override重写
重写注意事项
如果父类是protected的话重写必须要是protected 或者public
重写toString方法
toString是继承于object的
子类访问的成员和成员变量是就近原则
访问时候现在子类局部范围中去找,再去子类成员范围找,再去父类成员范围找,如果没有就报错。
super
super可以访问父类中的方法
子类构造器
在进行继承时候子类会先去调用父类构造器,再去调用子类构造器
class F{
// public F(){
// System.out.println("===父类F的 无参数构造器 执行了===");
// }
public F(String name, int age){
}
}
class Z extends F{
public Z(){
// super(); // 默认存在的
super("播妞", 17);
System.out.println("===子类Z的 无参数构造器 执行了===");
}
public Z(String name){
// super(); // 默认存在的
super("播妞", 17);
System.out.println("===子类Z的 有参数构造器 执行了===");
}
}
public class Test {
public static void main(String[] args) {
// 目标:先认识子类构造器的特点,再掌握这个特点的常见应用场景。
Z z = new Z();
Z z2 = new Z("播妞");
}
}子类继承父类时,子类中的构造器中都会有super这个函数(默认存在的)
为什么说要先调用父类的构造器,是因为要让更加完整。
this(。。。。)调用兄弟构造器
调用构造方法
public Student(String name, int age){
this(name, age, "黑马程序员");
}
public Student(String name, int age, String schoolName) {
super();
= name;
= age;
this.schoolName = schoolName;
}在
public Student(String name, int age){ this(name, age, "黑马程序员");}
其实就是调用了public Student(String name, int age, String schoolName)
注意事项
this构造器和super构造器不能同时存在
因为this构造器是调用兄弟构造器,而兄弟构造器里面有super 构造器
所以就会执行super构造器
在static修饰的地方没办法用super和this关键字
重写与重载
1. 重写(Override)
存在于继承体系中,指子类实现了一个与父类在方法声明上完全相同的一个方法。
为了满足里式替换原则,重写有以下三个限制:
• 子类方法的访问权限必须大于等于父类方法;
• 子类方法的返回类型必须是父类方法返回类型或为其子类型。
• 子类方法抛出的异常类型必须是父类抛出异常类型或为其子类型。
使用 @Override 注解,可以让编译器帮忙检查是否满足上面的三个限制条件。
下面的示例中,SubClass 为 SuperClass 的子类,SubClass 重写了 SuperClass 的 func() 方法。其中:
• 子类方法访问权限为 public,大于父类的 protected。
• 子类的返回类型为 ArrayList<Integer>,是父类返回类型 List<Integer> 的子类。
• 子类抛出的异常类型为 Exception,是父类抛出异常 Throwable 的子类。
• 子类重写方法使用 @Override 注解,从而让编译器自动检查是否满足限制条件。
class SuperClass {
protected List<Integer> func() throws Throwable {
return new ArrayList<>();
}
}
class SubClass extends SuperClass {
@Override
public ArrayList<Integer> func() throws Exception {
return new ArrayList<>();
}
}在调用一个方法时,先从本类中查找看是否有对应的方法,如果没有再到父类中查看,看是否从父类继承来。否则就要对参数进行转型,转成父类之后看是否有对应的方法。总的来说,方法调用的优先级为:
• (this)
• (this)
• (super)
• (super)
/*
A
|
B
|
C
|
D
*/
class A {
public void show(A obj) {
System.out.println("A.show(A)");
}
public void show(C obj) {
System.out.println("A.show(C)");
}
}
class B extends A {
@Override
public void show(A obj) {
System.out.println("B.show(A)");
}
}
class C extends B {
}
class D extends C {
}public static void main(String[] args) {
A a = new A();
B b = new B();
C c = new C();
D d = new D();
// 在 A 中存在 show(A obj),直接调用
a.show(a); // A.show(A)
// 在 A 中不存在 show(B obj),将 B 转型成其父类 A
a.show(b); // A.show(A)
// 在 B 中存在从 A 继承来的 show(C obj),直接调用
b.show(c); // A.show(C)
// 在 B 中不存在 show(D obj),但是存在从 A 继承来的 show(C obj),将 D 转型成其父类 C
b.show(d); // A.show(C)
// 引用的还是 B 对象,所以 ba 和 b 的调用结果一样
A ba = new B();
ba.show(c); // A.show(C)
ba.show(d); // A.show(C)
}2. 重载(Overload)
存在于同一个类中,指一个方法与已经存在的方法名称上相同,但是参数类型、个数、顺序至少有一个不同。
应该注意的是,返回值不同,其它都相同不算是重载。
class OverloadingExample {
public void show(int x) {
System.out.println(x);
}
public void show(int x, String y) {
System.out.println(x + " " + y);
}
}public static void main(String[] args) {
OverloadingExample example = new OverloadingExample();
example.show(1);
example.show(1, "2");
}
2024-07-07
浏览10
学习笔记
登录后评论
点赞
评论
分享