一、继承
理解继承
Cat继承了Animal类,其中:Animal类称为父类/基类或超类,Cat可以称为Animal的 子类/派生类,继承之后,子类可以复用父类中成员,子类在实现时只需关心自己新增加的成员即可
Java中不支持多继承,仅支持A extends B 单继承//A extends B B extends C 多层继承 //A extends C B extends C 不同类继承自同一类。
public class TestExtend {
public static void main(String[] args) {
Dog d1 =new Dog();
d1.name = "xiaocs";
d1.age = 15;
Cat c1 = new Cat();
c1.color = "red";
c1.type = "波斯";
c1.friendly();
}
}
/**
* Dog未继承animal则无法调用animal中的成员变量和成员方法
*/
class Dog{
public int age;
public String name;
public void shot(){
System.out.println("汪汪汪");
}
}
//cat可以直接调用animal中的成员变量和成员方法
class Cat extends animal{
public int weight;
public String sex;
public void eat(){
System.out.println("嘎嘎吃");
}
}
class animal{
public String color;
public String type;
public void friendly(){
System.out.println("对人类友好");
}
}
子类访问父类
子类和父类不存在同名成员变量
public class Base {
int a;
int b;
}
public class Derived extends Base{
int c;
public void method(){
a = 10; // 访问从父类中继承下来的a
b = 20; // 访问从父类中继承下来的b
c = 30; // 访问子类自己的c
}
子类和父类成员变量同名
public class Base {
int a;
int b;
int c;
}
public class Derived extends Base{
int a; // 与父类中成员a同名,且类型相同
char b; // 与父类中成员b同名,但类型不同
public void method(){
a = 100;
b = 101;
c = 102; // 子类没有c,访问的肯定是从父类继承下来的c
// d = 103; // 编译失败,因为父类和子类都没有定义成员变量b
}
}
成员变量访问遵循就近原则,自己有优先自己的,与父类同名也优先访问自己的,如果没有则向父类中找。
成员方法亦然,如果子类有则先访问子类的,子类没有先访问父类的,如果存在方法重载,则根据引用的情况,选择合适的方法
在子类方法中,如果想要明确访问父类中成员时,借助super关键字即可
二、super关键字
当父类和子类的成员变量或成员方法相同时,调用父类的成员变量或方法,使用super关键字
class Cat extends animal{
public int color;
public String type;
public void eat(){
//调用父类的成员变量
super.color = "red";
super.type = "波斯";
super.friendly();
System.out.println("嘎嘎吃");
}
}
class animal{
public String color;
public String type;
public void friendly(){
System.out.println("对人类友好");
}
}
子类的构造方法(无参数)
若父类显式定义无参或者默认的构造方法,在子类构造方法第一行默认有隐含的super()调用,即调用基类构造方法
public class TestExtend {
public static void main(String[] args) {
Cat c = new Cat();
}
}
class Cat extends animal{
public int size;
public String name;
public Cat(){
// super();
//注意子类构造方法中默认会调用基类的无参构造方法:super(),
// 用户没有写时,编译器会自动添加,而且super()必须是子类构造方法中第一条语句,
// 并且只能出现一次
System.out.println("Cat::");
}
public void eat(){
System.out.println("嘎嘎吃");
}
}
class animal{
public String color;
public String type;
public animal() {
System.out.println("animal::");
}
public void friendly(){
System.out.println("对人类友好");
}
}
子类对象构造时,需要先调用父类构造方法,然后执行子类的构造方法。
子类的构造方法(有参数)
如果父类构造方法是带有参数的,此时需要用户为子类显式定义构造方法,并在子类构造方法中选择合适的父类构造方法调用,否则会编译失败
public class TestExtend {
public static void main(String[] args) {
Cat c = new Cat("red","波斯",45,"xiaos");
}
}
class Cat extends animal{
public int size;
public String name;
public Cat(String color, String type, int size, String name) {
super(color, type);
this.size = size;
this.name = name;
}
public void eat(){
System.out.println("嘎嘎吃");
}
}
class animal{
public String color;
public String type;
public animal(String color, String type) {
this.color = color;
this.type = type;
}
public void friendly(){
System.out.println("对人类友好");
}
}
在子类构造方法中,super(...)调用父类构造时,必须是子类构造函数中第一条语句。
super(...)只能在子类构造方法中出现一次,并且不能和this同时出现
✅super和this之间的区别?
相同点:
1.都属于java 中的关键字
2.只能在类的非静态方法中使用,用来访问 非静态的方法和字段
3.在构造 方法中使用时必须是构造方法当中的第一条语句,并且二者不能同时存在
不同点:
1.this指的是当前对象的引用,super指的是当前对象对父类部分对象的使用
在非静态成员方法中,this用来访问本类的方法和属性,super用来访问父类继承下来的方法和属性
在构造方法当中,this用于调用本类的构造方法,super调用父类的构造方法,两种调用不能同时在构造方法中出现
构造方法中一定会存在super(...)的调用,用户没有写编译器也会增加,但是this(...)用户不写则没有
三、继承关系下的代码块
public class TestExtend {
public static void main(String[] args) {
Cat c = new Cat("red","波斯",45,"xiaos");
}
}
class Cat extends animal{
public int size;
public String name;
//5.子类的实例代码块
{
System.out.println("cat::实例");
}
//2.子类的静态代码块
static{
System.out.println("cat::static");
}
//6.子类的构造方法
public Cat(String color, String type, int size, String name) {
super(color, type);
this.size = size;
this.name = name;
System.out.println("cat::构造");
}
public void eat(){
System.out.println("嘎嘎吃");
}
}
class animal{
public String color;
public String type;
//3.父类的实例代码块
{
System.out.println("animal::实例");
}
//1。父类的静态代码块
static{
System.out.println("animal::static");
}
//4.父类的构造方法
public animal(String color, String type) {
this.color = color;
this.type = type;
System.out.println("animal::构造");
}
public void friendly(){
System.out.println("对人类友好");
}
根据执行结果可以的出以下结论:
父类的静态代码块>>子类的静态代码块>>父类的实例代码块>父类的构造方法>>子类的实例代码块>> 子类的构造方法
第二次实例化子类对象时,父类和子类的静态代码块都将不会再执行
四、protected关键字
访问限定:同一个包中的类和不同包中的子类
package TestDemo2;
public class B {
private int a;
protected int b;
public int c;
int d;
}
在不同包中即package TestDemo 中
只有public和protected修饰的成员可以访问
五、final关键字
修饰变量时: 表示常量即不能修改
final int a = 10;
a = 20; // 编译出错
修饰类时: 表示此类不能被继承,即不能作为父类
//final修饰标签:初阶,Java,String,构造方法,子类,animal,父类,public,三大 From: https://blog.51cto.com/u_15733182/5946742
final class animal{
public String color;
public String type;
public animal(String color, String type) {
this.color = color;
this.type = type;
System.out.println("animal::构造");
}
}