title: 面向对象思想
date: 2019-03-22 23:24:52
categories: 代码
tags: java

一、三大特性

封装

封装从字面上来理解就是包装的意思,专业一点就是信息的隐藏,是指利用抽象数据类型将数据和基于数据的操作封装在一起,使其成为一个不可分割的独立个体,数据被保护在抽象数据类型的内部 ,尽可能地隐藏内部的细节,只保留一些对外接口使之与外部发生联系。系统的其他对象只能通过包裹在数据外面的已经授权的操作来与这个封装的对象进行交流和交互。也就是说用户是无需知道对象内部的细节(当然也无从知道),但可以通过该对象对外的提供的接口来访问该对象。

优点:

  • 减少耦合:可以独立地开发、测试、优化、使用、理解和修改
  • 减少维护的负担: 可以更容易被程序员理解,并且在调试的时候可以不影响其他模块
  • 有效的调节性能: 可以通过剖析确定哪些模块影响了系统的性能
  • 提高软件的可重用性
  • 降低大型系统的风险: 即使整个系统不可用,但是这些独立的模块是可用的

以下 Person 类封装 name、gender、age 等属性,外界只能通过 get() 方法获取一个 Person 对象的 name 属性和 gender 属性,而无法获取 age 属性,但是 age 属性可以供 work() 方法使用。

注意到 gender 属性使用 int 数据类型进行存储,封装使得用户注意不到这种实现细节。并且在需要修改 gender 属性使用的数据类型时,也可以在不影响客户端代码的情况下进行。

  1. public class Person {
  2. private String name;
  3. private int gender;
  4. private int age;
  5. public String getName() {
  6. return name;
  7. }
  8. public String getGender() {
  9. return gender == 0 ? "man" : "woman";
  10. }
  11. public void work() {
  12. if (18 <= age && age <= 50) {
  13. System.out.println(name + " is working very hard!");
  14. } else {
  15. System.out.println(name + " can't work any more!");
  16. }
  17. }
  18. }

继承

继承实现了 IS-A 关系,例如 Cat 和 Animal 就是一种 IS-A 关系,因此 Cat 可以继承自 Animal,从而获得 Animal 非 private 的属性和方法。

继承应该遵循里氏替换原则,子类对象必须能够替换掉所有父类对象。

上张图来看看继承关系:

{% asset_img 继承.png 继承 %}
继承.png

Cat 可以当做 Animal 来使用,也就是说可以使用 Animal 引用 Cat 对象。父类引用指向子类对象称为 向上转型 。

  1. Animal animal = new Cat();

多态

多态分为编译时多态和运行时多态:

  • 编译时多态主要指方法的重载
  • 运行时多态指程序中定义的对象引用所指向的具体类型在运行期间才确定

运行时多态有三个条件:

  • 继承
  • 覆盖(重写)
  • 向上转型

多态通过分离做什么和怎么做,从另一个角度将接口和实现分离开来。多态不但能够改善代码的组织结构和可读性,还能够创建可扩展的程序——-即无论在项目最初创建时还是在需要添加新功能时都可以“生长”的程序。

下面的代码中,乐器类(Instrument)有两个子类:Wind 和 Percussion,它们都覆盖了父类的 play() 方法,并且在 main() 方法中使用父类 Instrument 来引用 Wind 和 Percussion 对象。在 Instrument 引用调用 play() 方法时,会执行实际引用对象所在类的 play() 方法,而不是 Instrument 类的方法。

  1. public class Instrument {
  2. public void play() {
  3. System.out.println("Instument is playing...");
  4. }
  5. }
  6. public class Wind extends Instrument {
  7. public void play() {
  8. System.out.println("Wind is playing...");
  9. }
  10. }
  11. public class Percussion extends Instrument {
  12. public void play() {
  13. System.out.println("Percussion is playing...");
  14. }
  15. }
  16. public class Music {
  17. public static void main(String[] args) {
  18. List<Instrument> instruments = new ArrayList<>();
  19. instruments.add(new Wind());
  20. instruments.add(new Percussion());
  21. for(Instrument instrument : instruments) {
  22. instrument.play();
  23. }
  24. }
  25. }

类图

待补

设计原则

待补