面向对象
### 一、内容回顾
封装:将类内部的实现(属性)隐藏(private)在类的内部,通过对外的公共接口(public setXXX getXXX)去操作,确保数据的安全(合理)。
过程
1. 属性私有
2. 封装方法
3. 在setXXX方法中对值的范围进行判断
继承:描述类和类之间的一种关系,通过这种关系子类就可以访问父类中可以访问的成员。
好处:代码复用,结构清晰(父类中存放公共的成员,子类存放独有成员)
实现:子类 extends 父类
特点:单继承,传递性
子类继承了父类中的那些成员
- public 公共的
- 同一包中的子类,继承父类的默认访问修饰符的成员。
- protected 受保护的
二、今日内容
- 各种访问修饰符 总结
- 继承的本质
- 多态及多态的应用。
- 面向对象的应用
- 关键字:static final abstract
1、 各种访问修饰符 总结
本类 | 同包类 | 同包子类 | 不同包子类 | 不同包类 | |
---|---|---|---|---|---|
private | √ | × | × | × | × |
默认(无) | √ | √ | √ | × | × |
protected | √ | √ | √ | √ | × |
public | √ | √ | √ | √ | √ |
说明:
默认访问修饰符,具有包内可见性,无论是否为子类,都能防 嗯。受保护的,包内可见,子类可见。
受保护的:堡内可见,子类可见
修饰类:public 默认的
修饰属性,方法:private 默认的 protected public
局部变量:不适用任何修饰符,使用默认
2.继承的本质
枚举类型:一种数据类型,把变量可能出现的值一一列举出
e.g 男,女 司机:春夏秋冬 一年的月份 一周的天数
作用:给枚举类型变量赋值的时候,只能赋值枚举列出的值
本质:创建子类对象之前,先创建其父类对象。
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-zrRafbfP-1628510444929)(…\img\extends.png)]
3.方法重写
提问:什么是方法重载?
面试题:方法重载和方法重写的区别?
问题:父类中无法确定方法体
解决:1. 在父类中编写方法–虚方法
2.在子类中重写父类中的方法
重写规则:
1.重写的方法(子类)访问修饰符不能比被重写的方法(父类)的访问修饰符更严格(小)
2.方法头相同
方法重写/方法覆盖:在子类中重写父类中的方法,
原理:在巡行过程中,也就是方法调用过程中,子类的方法把父类的方法覆盖掉了。
面试题:方法重载和方法重写的区别
super:父类对象,通过哪个子类对象访问,就代表哪个子类的父类对象
super的作用:
-
可以使用super来访问尼夫雷中的成员,很好的区分开哪些成员是子类的成员(this),哪些是父类的
public void sayHi() { System.out.println("输出宠物:"+super.getName()+"品种:"+strain); }
-
可以调用父类中的构造方法。
//3个参数
public Dog(String name,AnimalSex sex,String strain) {
//通过super关键字,调用父类有参构造方法
super(name,sex);
this.strain=strain;
}
5.明确
- 子类中的方法可以和父类相同–方法重写
- 子类中的属性可以和父类相同–属性不会重写 需要通过super或this调用
继承:概念
- 语法:子类 extends 父类
- 特点:单继承,传递性
子类继承了父类的哪些成员
4个访问修饰符的访问权限
- 继承的本质:对象的创建顺序
- 方法重写
- super关键字的使用
6.多态
问题:方法的菜蔬是子类类型,有多少个子类
public class Master {
private String name;
//主人喂养宠物,参数是需要喂养的宠物
public void feed(Dog dog) {
System.out.println("主人"+this.name+"正在喂养宠物:"+dog.getName());
System.out.println(dog.getName());
dog.eat();
}
//方法重载,参数是Cat
public void feed(Cat cat) {
System.out.println("主人"+this.name+"正在喂养宠物:"+cat.getName());
System.out.println("宠物"+cat.getName());
cat.eat();
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
解决问题的方法:使用多态–优化方法
解决步骤:
- 在父类中编写方法
public void eat() {
//由于在父类中,无法确定哪种动物,所以无法确定方法体
}
-
在子类中重写父类中的方法
public void eat() {//dog System.out.println("吃骨头"); }
public void eat() {//cat System.out.println("吃鱼"); }
-
在使用的时候用父类类型做参数类型
Master类中
public void feed(Animal animal) { System.out.println("主人"+this.name+"正在喂养"+animal.getName()); System.out.println("宠物:"+animal.getName()); animal.eat(); }
测试类
Dog wangcai=new Dog("旺财",AnimalSex.雄性,"拉布拉多"); Cat huanhuan=new Cat("欢欢",AnimalSex.雌性,"胖橘"); Master zhangsan = new Master(); zhangsan.setName("张三"); //喂养宠物 //类型是父类,赋值为类---里氏代换原则 LSP zhangsan.feed(wangcai); zhangsan.feed(huanhuan);
概念:同一父类类型,对同意方法表现出不同的状态,成为多态
堕胎具备的要素:
- 父类 方法
- 子类 不同子类以不同的方式来重写父类的方法
- 父类类型 赋值子类对象
案例:人类,吃饭方法
中国人类:吃饭呢方法–用筷子吃
美国人类:吃饭方法–用刀叉吃
人类:zhangsan=new meiguoren();
人类:lisi = new zhongguoren();
zhangsan.eat();
lisi.eat();
多态的好处:代码简洁,适用于程序的扩展
多态使用的技术:继承 方法重写 LSP(父类的引用指向子类)
梳理多态:优化方法的
在不适用多态时
各子类都有eat方法
方法的参数只能是子类类型
问题:子类越多,重载的喂养方法feed方法,就越多,再增加子类类型是,还需要增加方法,编写大量的方法
解决方法
使用多态
- 在父亲类中编写方法
- 子类重写父类方法
- 使用时用父类做类型,赋值子类对象
【说明】:类型是父类,即使赋值子类对象,在访问时,依然只能访问父类,及父类的父类成员,子类是无法访问的。
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-uu7Zy3xh-1628510444932)(…\img\duotai)]
类中编写方法
2. 子类重写父类方法
3. 使用时用父类做类型,赋值子类对象
【说明】:类型是父类,即使赋值子类对象,在访问时,依然只能访问父类,及父类的父类成员,子类是无法访问的。
- 父类 方法