Java基础【之】面向对象编程(封装、继承、多态、代码实现)
1.封装
- 封装的目的:一个类,封装后,只对外提供交互方法,实现“高内聚,低耦合”。
- 高内聚 :复杂的功能,在类的内部实现,不需要外部参与逻辑实现;
- 低耦合 :仅对外部访问,提供访问方法。
- 实现:依靠
private
与 public
两种访问权限。
class People {
private int age = 0;
private String name = null;
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
public class FengZhuang {
public static void main(String[] args) {
People people = new People();
System.out.println(people.getName() + " : " + people.getAge());
people.setName("小明");
people.setAge(20);
System.out.println(people.getName() + " : " + people.getAge());
}
}
2.继承
2.1.extends
- 继承
当多个类中,存在相同属性和行为,可以抽象出一个父类,多个类继承这个父类,就可以省去定义的步骤。
子类继承了父类,就继承了父类的方法和属性。
子类中,可以使用父类中定义的方法和属性,也可以创建新的数据和方法。 - 语法:使用关键字 extends
class 子类 extends 父类{ }
- 作用:
减少了代码冗余,提高了代码的复用性,利于功能的扩展。
类与类之间产生了关联关系,是实现多态的前提。 - 注意:
子类不能直接访问父类中私有的(private)的成员变量和方法。
不允许多重继承 , 一个子类只能有一个父类 , 一个父类可以有多个子类。
业务实现的过程中,不可以为了继承而继承,要有关联关系作为前提。 - 比如:
学生类
可以继承人类
并获得姓名
的属性
但是学生类
不可以为了获得个人所属学校
,而去继承学校类
。
class Person {
public String name;
}
class Student extends Person {
}
class Teacher extends Person {
}
public class JiCheng {
public static void main(String[] args) {
Student student = new Student();
student.name = "学生";
Teacher teacher = new Teacher();
teacher.name = "老师";
}
}
2.2.方法重写
- 方法重写
子类可以对从父类中继承来的方法进行改造,在程序执行时,子类的方法将覆盖父类的方法。 - 注意:
1.子类重写的方法,必须和父类被重写的方法,具有相同的方法名称、参数列表。
2.子类重写方法的返回值类型,不能大于父类被重写的方法的返回值类型。
3.子类重写的方法,访问权限,不能小于父类被重写的方法。
4.子类不能重写父类中声明为 private 的方法。
5.子类方法抛出的异常,不能大于父类被重写方法的异常。
6.子类无法覆盖父类的,静态方法。
class Person {
public String name;
public void printName() {
System.out.println("Person名为:" + name);
}
}
class Student extends Person {
public void printName() {
System.out.println("学生名:" + name);
}
}
class Teacher extends Person {
public void printName() {
System.out.println("老师名:" + name);
}
}
public class JiCheng{
public static void main(String[] args) {
Person person = new Person();
person.name = "路人";
person.printName();
Student student = new Student();
student.name = "学生";
student.printName();
Teacher teacher = new Teacher();
teacher.name = "老师";
teacher.printName();
}
}
2.3.super
- super
用来访问中定义的 属性、成员方法
子类可以在构造器中,调用父类的构造器
当父子类出现同名成员时,可以用super表明,调用的是父类中的成员
如果存在多层父类,会一直向上找,找到第一个满足条件的即可。
- super和this的用法相像,必须放在方法的首行,只能”二选一”。
- this代表本类对象的引用,super代表父类的内存空间的标识。
- 如果子类构造器中既未显式调用父类或本类的构造器,且父类中又没有无参的构造器,则编译出错。
- 注意:子类的构造函数首行,默认执行
super()
,除非手动指定super(参数列表)
class Person {
public String name;
public Person() {
System.out.println("Person无参构造函数");
}
public Person(String name) {
this.name = name;
System.out.println("Person有参构造函数:" + name);
}
}
class Student extends Person {
public Student() {
System.out.println("Student构造函数执行");
}
public Student(String name) {
super(name);
System.out.println("Student构造函数执行:" + name);
}
}
class Teacher extends Person {
public Teacher() {
System.out.println("Teacher构造函数执行");
}
public Teacher(String name) {
System.out.println("Teacher构造函数执行:" + name);
}
}
public class JiCheng {
public static void main(String[] args) {
Teacher teacher = new Teacher();
Student student = new Student();
Teacher teacher001 = new Teacher("老师001");
Student student001 = new Student("学生001");
}
}
3.多态
3.1.对象的多态、方法的多态
- 多态(动态绑定)
对象的多态:父类的引用指向子类的对象。
方法的多态:调用的是父类对象的方法,实现的是子类对象
- 方法的重载与重写
- 重写:发生在父子类之间,名称相同,参数相同的两个方法,重写是多态的前提条件
- 重载:发生在一个类中,名称相同的多个方法,参数列表不相同,叫做方法重载
- 方法的重载不叫多态,只是一种编程模式
3.2.动态绑定
- 动态绑定
只有等到方法调用的那一刻,解释运行器才会确定所要调用的具体方法,这称为“动态绑定
”
编译时和运行时不一致,就出现了对象和方法的多态性(Polymorphism)
父类的类型,不能再访问子类中,独有的属性和方法 - 引用类型变量,可能指向多种不同类型的对象。
3.3.向上转型(upcasting)
- 向上转型(upcasting)
父类的引用指向子类的对象 (子类可看做是特殊的父类)
3.4.instanceof
- instanceof:判断对象的类型,返回 true/false
- 语法:
对象实例 instanceof 类名
3.5.数据类型转换
- 基本数据类型:
- 自动类型转换:小的数据类型可以自动转换成大的数据类型
long g=2000; double d=1000.0f
- 强制类型转换:可以把大的数据类型强制转换(casting)成小的数据类型如
float f=(float)1.0; int a=(int)1000L
- 引用数据类型
- 子类到父类的类型转换自动进行
- 父类到子类的类型转换,必须通过强转
(类型)对象 Object obj = "123"; String objStr = (String) obj;
- 无继承关系的引用类型间的转换是非法的
- 在强转之前,可以用instanceof测试
4.代码实现
4.1.类实现
- 牛和老鼠都是动物,抽象出动物类,都具备名称的属性,都具备发出叫声的方法。
- 由各自具体实现类,去实现不同的叫声
abstract class AnimalClass {
String name;
abstract void jiao();
public AnimalClass(String name) {
this.name = name;
}
}
class 老鼠 extends AnimalClass {
public 老鼠(String name) {
super(name);
}
@Override
void jiao() {
System.out.println(name + ":是一只老鼠:吱吱吱~~~");
}
}
class 牛 extends AnimalClass {
public 牛(String name) {
super(name);
}
@Override
void jiao() {
System.out.println(name + ":是一头牛:哞哞哞~~~");
}
}
public class DuoTai {
public static void main(String[] args) {
AnimalClass ls = new 老鼠("图奇");
ls.jiao();
AnimalClass niu = new 牛("阿利斯塔");
niu.jiao();
}
}
4.2.接口实现
- 牛和老鼠都是动物,抽象出动物类接口,都具备名称的属性,都具备发出叫声的方法。
- 由各自具体实现类,去实现不同的叫声
interface AnimalInterface {
void jiao();
}
class 老鼠 implements AnimalInterface {
String name;
public 老鼠(String name) {
this.name = name;
}
@Override
public void jiao() {
System.out.println(name + ":是一只老鼠:吱吱吱~~~");
}
}
class 牛 implements AnimalInterface {
String name;
public 牛(String name) {
this.name = name;
}
@Override
public void jiao() {
System.out.println(name + ":是一头牛:哞哞哞~~~");
}
}
public class DuoTai {
public static void main(String[] args) {
AnimalInterface ls = new 老鼠("图奇");
ls.jiao();
AnimalInterface niu = new 牛("阿利斯塔");
niu.jiao();
}
}
《上一篇:类、面向过程、面向对象、对象、属性、行为》
《目录:Java渐进式学习》
《幕》
- 留白 —<老吉>
- ~ 今 ~ ❀ ~ ❀❀❀❀❀❀❀❀❀❀ ❀❀❀❀❀❀❀❀❀❀ ❀❀❀❀❀❀❀