面向对象编程(封装、继承、多态)

封装、多态和继承是面向对象编程的三大特性

除了以上三大特征,我们也要熟悉其他概念,例如包,组合,抽象类,接口等。

封装

<< 代码大全 >> 开篇就在讨论一个问题 : 软件开发的本质就是对程序复杂程度的管理 . 如果一个软件代码复杂程
度太高 , 那么就无法继续维护 . 如何管理复杂程度 ? 封装就是最基本的方法 .
在我们写代码的时候经常会涉及两种角色 : 类的实现者 类的调用者 .
封装的本质就是让类的调 用者不必太多的了解类的实现者是如何实现类的, 只要知道如何使用类就行了.这样就降低了类使用者的学习和使用成本 , 从而降低了复杂程度。

private实现封装

private/ public 这两个关键字表示 "访问权限控制"

  被 public 修饰的成员变量或者成员方法 , 可以直接被类的调用者使用 .
  被 private 修饰的成员变量或者成员方法 , 不能被类的调用者使用.

包(package)是组织类的一种方式

使用包主要目的是保证类的唯一性

可以使用import语句导入包,如果需要java.util中的其他类,可以使用ipmore java.util.*(但是是我们更建议显式的指定要导入的类名. 否则还是容易出现冲突的情况.)

包的访问权限控制

我们已经了解了类中的 public private. private 中的成员只能被类的内部使用 .
如果某个成员不包含 public private 关键字 , 此时这个成员可以在包内部的其他类使用 , 但是不能在包外部的类使用 .

常见的系统包

1. java.lang: 系统常用基础类 (String Object), 此包从 JDK1.1 后自动导入。
2. java.lang.reflflect:java 反射编程包 ;
3. java.net: 进行网络编程开发包。
4. java.sql: 进行数据库开发的支持包。
5. java.util: java 提供的工具程序包。 ( 集合类等 ) 非常重要
6. java.io:I/O 编程开发包。

继承

背景

代码中创建的类 , 主要是为了抽象现实中的一些事物 ( 包含属性和方法 ).
有的时候客观事物之间就存在一些关联关系 , 那么在表示成类和对象的时候也会存在一定的关联 .
例如 , 设计一个类表示动物
// Animal.java 
public class Animal { 
 public String name; 
 
 public Animal(String name) { 
 this.name = name; 
 } 
 
 public void eat(String food) { 
 System.out.println(this.name + "正在吃" + food); 
 } 
} 
// Cat.java 
class Cat { 
 public String name; 
 
 public Cat(String name) { 
 this.name = name; 
 } 
 
 public void eat(String food) { 
 System.out.println(this.name + "正在吃" + food); 
 } 
} 
// Bird.java 
class Bird { 
 public String name; 
 
 public Bird(String name) { 
 this.name = name; 
 } 
 
 public void eat(String food) { 
 System.out.println(this.name + "正在吃" + food); 
 } 
 
 public void fly() { 
 System.out.println(this.name + "正在飞 ︿( ̄︶ ̄)︿"); 
 } 
}

这个代码我们发现其中存在了大量的冗余代码。 此时我们就可以让 Cat Bird 分别继承 Animal , 来达到代码重用的效果。

此时 , Animal 这样被继承的类 , 我们称为 父类 , 基类 超类 , 对于像 Cat Bird 这样的类 , 我们称为 子类 , 派生类和现实中的儿子继承父亲的财产类似 , 子类也会继承父类的字段和方法 , 以达到代码重用的效果。

语法规则

使用 extends 指定父类 .
Java 中一个子类只能继承一个父类.(单继承语言)
子类会继承父类的所有 public 的字段和方法.
对于父类的 private 的字段和方法 , 子类中是无法访问的 .
子类的实例中 , 也包含着父类的实例 . 可以使用 super 关键字得到父类实例的引用.

此时对于上面的代码我们就可以使用继承改进

class Animal { 
 public String name; 
 public Animal(String name) { 
 this.name = name; 
 } 
 public void eat(String food) { 
 System.out.println(this.name + "正在吃" + food); 
 } 
} 
class Cat extends Animal { 
 public Cat(String name) { 
 // 使用 super 调用父类的构造方法. 
 super(name); 
 } 
} 
class Bird extends Animal { 
 public Bird(String name) { 
比特科技
 super(name); 
 } 
 public void fly() { 
 System.out.println(this.name + "正在飞 ︿( ̄︶ ̄)︿"); 
 } 
} 
public class Test { 
 public static void main(String[] args) { 
 Cat cat = new Cat("小黑"); 
 cat.eat("猫粮"); 
 Bird bird = new Bird("圆圆"); 
 bird.fly(); 
 } 
}
如果我们把 name 改成 private, 那么此时子类就不能访问了,此时我们就可以使用protected关键字.

protected关键字

刚才我们发现 , 如果把字段设为 private, 子类不能访问 . 但是设成 public, 又违背了我们 " 封装 " 的初衷 .两全其美的办法就是 protected 关键字。
对于类的调用者来说 , protected 修饰的字段和方法是不能访问的
对于类的 子类 同一个包的其他类 来说 , protected 修饰的字段和方法是可以访问的
小结 : Java 中对于字段和方法共有四种访问权限
private: 类内部能访问 , 类外部不能访问
默认 ( 也叫包访问权限 ): 类内部能访问 , 同一个包中的类可以访问 , 其他类不能访问 .
protected: 类内部能访问 , 子类和同一个包中的类可以访问 , 其他类不能访问 .
public : 类内部和类的调用者都能访问
访问权限:public>protected>default>private
final 关键字
final 关键字的功能是 限制 类被继承

组合

和继承类似 , 组合也是一种表达类之间关系的方式 , 也是能够达到代码重用的效果。
组合表示 has - a 语义
继承表示 is - a 语义

多态(难点)

向上转型

子类对象/引用 给父类就称为向上转型。

注:向上转型之后 只能通过父类的引用访问父类自己特有的方法和属性,不能访问子类特有的属性和方法

向下转型(不推荐)

向上转型是子类对象转成父类对象 , 向下转型就是父类对象转成子类对象 . 相比于向上转型来说 , 向下转型没那么常见 ,但是也有一定的用途

动态绑定(运行时绑定)

满足条件:1.向上转型 2.通过父类引用调用父类和子类的同名覆盖方法,此时就会发生运行时绑定。那么覆盖又是什么意思呢?

方法重写

子类实现父类的同名方法 , 并且参数的类型和个数完全相同 , 这种情况称为 覆写 / 重写 / 覆盖 (Override)
注意事项:
1.重写中子类的方法的访问权限不能低于父类的方法访问权限 .
2.重写的方法返回值类型不一定和父类的方法相同 ( 但是建议最好写成相同 , 特殊情况除外 )
3.普通方法可以重写 , static 修饰的静态方法不能重写 .
4.private方法也不可以重写
5.如果一个方法被final修饰,也不可以被重写

理解多态

多态顾名思义, 就是 "一个引用, 能表现出多种不同形态"
无论是哪种编程语言 , 多态的核心都是让调用者 不必关注对象的具体类型 . 这是降低用户使用成本的一种重要方式

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值