网站首页 > 资源文章 正文
前言
作为文集的第一篇,我觉得有必要介绍一下大概的写作规划。整个文集将分为三个部分,分别是面向对象六大原则、23种设计模式,以及MVC、MVP、MVVM三种应用架构的介绍和使用。
如果大家看过何红辉和关爱民老师著的《Android源码设计模式解析与实战》,就会觉得似曾相识。其实,我写这个文集的目的,就是为了巩固我看这本书后的感悟,让我能加深对内容的理解。
像我们平时工作,通常都是先实现所给的功能,等到修改或者扩展时,发现不方便,再结合问题重构模块。其实有些是可以避免的,面向对象六大原则在类这个层次上告诉我们,如何构造类、如何维护类之间的关系;23种设计模式在功能的层次上指导我们写出精炼完善的代码;而应用架构的变迁反映了App层次上应用功能、资源的增加,导致维护成本的提高,急需细化模块。
1、现实中的场景
有一个工厂想生产一款产品,按照流程得先产生设计稿,然后根据设计稿做出产品原型,最后生产出产品。
2、代码描述现象
新建一个项目,用Factory代表工厂,通过productA方法显示生产产品A的流程,最后在程序入口Main中调用。
public class Factory { public Factory() { super(); } public void productA() { System.out.println("产生设计稿A"); System.out.println("做出产品原型A"); System.out.println("生产出产品A"); } }
public class Main { public static void main(String[] args) { new Factory().productA(); } }
3、单一职责原则
定义:一个类,应该仅有一个引起它变化的原因。
目的:让一个类专注于自身的功能。
实例:我们来看看上面的案例,明显可以发现工厂的功能过于复杂,又是设计又是做原型又是生产,随着业务的增加会越来越臃肿,不方便管理,所以应该将设计和原型交给专业的第三方来做。根据这个原则,可以将代码做如下修改:
public class DesignerA { public DesignerA() { super(); } public void design() { System.out.println("产生设计稿A"); } }
public class CompanyA { public CompanyA() { super(); } public void make() { System.out.println("做出产品原型A"); } }
public class Factory { private DesignerA mDesigner; private CompanyA mCompany; public Factory() { super(); mDesigner = new DesignerA(); mCompany = new CompanyA(); } public void productA() { mDesigner.design(); mCompany.make(); System.out.println("生产出产品A"); } }
总结:Factory的代码减少了,功能更明确了。当设计团队和原型公司内部发生变化时,不会影响工厂的生产流程。
4、开闭原则(由里氏替换原则、依赖倒置原则实现)
定义:类、模块、函数等应该对于扩展是开放的,对于修改是封闭的。
目的:在软件扩展的过程中,确保原有功能的正确性。
实例:上面的案例,已经细分了生产责任。我们就工厂来看,如果接到了公司B的产品原型咋办,现在而言是生产不了的,没那功能呀。所以得增加功能:
public class Factory { // 一些相关的初始化工作 public void productA() { mDesigner.design(); mCompany.make(); System.out.println("生产出产品A"); } public void productB() { // 关于产品B的设计、原型和生产 } }
可是,随着工厂的发展,功能会不断增加,总不能每次都整改工厂吧。所以,我们可以通过父类(里氏替换原则)或者接口(依赖倒置原则)来确定生产规范,符合的产品,工厂就能生产。下面用里氏替换原则做个示范:
// 声明设计的规范 public abstract class Designer { public Designer() { super(); // 此处是子类不需要的 System.out.println("开始进行产品设计"); } public abstract void design(); }
// 声明原型的规范 public abstract class Company { public Company() { super(); // 此处是子类不需要的 System.out.println("根据设计做原型"); } public abstract void make(); }
// 符合规范的设计师A public class DesignerA extends Designer { public DesignerA() { super(); } @Override public void design() { System.out.println("产生设计稿A"); } }
// 符合规范的产品公司A public class CompanyA extends Company { public CompanyA() { super(); } @Override public void make() { System.out.println("做出产品原型A"); } }
public class Factory { private Designer mDesigner; private Company mCompany; // 工厂根据不同的设计和原型生产 public Factory(Designer designer, Company company) { super(); mDesigner = designer; mCompany = company; } public void product() { mDesigner.design(); mCompany.make(); System.out.println("生产出所需的产品"); } }
public class Main { public static void main(String[] args) { // 拿到设计图和产品原型,开始生产 new Factory(new DesignerA(), new CompanyA()).product(); } }
区别:继承父类和实现接口的区别就是里氏替换和依赖倒置的区别。继承可以拥有父类的所有属性和方法,减少创建类的成本,但同时会造成系统耦合,子类代码冗余,灵活性降低。接口正好相反,与之互补。
总结:开闭原则在工作中一定要实现,至于是用里氏替换还是依赖倒置,就根据当时的需求分析。
5、接口隔离原则
定义:类所依赖的接口应该仅仅包含所需要的功能。
目的:使接口的功能更加具体,类似单一职责,不过这是用于接口,使调用者只关注自己所需的功能。
实例:就拿声明设计规范的Designer来说,根据依赖倒置原则,将其改为接口,为了比较说明,添加了作为人所具有的吃饭的能力:
public interface Designer { // 此处声明设计师具有吃饭的能力 // 与为工厂设计图纸不相关,理应去掉 void eat(); void design(); }
总结:隐藏非相关功能,除了不暴露更多细节,增加用户学习成本,更能降低系统耦合性,提高应用灵活性。
6、迪米特原则
定义:一个类应该仅仅依赖于自己需要调用的对象。
目的:保证逻辑结构的清晰,降低系统的耦合程度。
实例:就拿负责生产的Factory来说,它同时含有Designer和Company。也就是只负责生产的工厂却要自己准备设计图纸和产品原型,这不符合现实情况,它应该只生产所有公司交给它的规范的产品:
public abstract class Company { // 由公司和设计师打交道 private Designer mDesigner; public Company(Designer designer) { super(); designer.design(); System.out.println("根据设计做原型"); } public abstract void make(); }
public class Factory { // 工厂只和公司拿来的原型打交道 private Company mCompany; public Factory(Company company) { super(); mCompany = company; } public void product() { mCompany.make(); System.out.println("生产出所需的产品"); } }
public class Main { public static void main(String[] args) { // 生产之前确定使用哪个公司的哪个设计师作品 new Factory(new CompanyA(new DesignerA())).product(); } }
总结:通过对结果进行比较,发现修改后(右)的流程比修改前(左)的流程更加符合现实生产环境。
写在最后:欢迎留言讨论,需要Java进阶资料私信“Java”或“架构资料”,加关注,持续更新!
猜你喜欢
- 2024-09-18 无门槛快速学编程——Python小短课,三探面向对象
- 2024-09-18 Python中的“实例化对象”——掌握面向对象编程的核心技能
- 2024-09-18 面向过程和面向对象最通俗的解释(面向对象和面向过程的概念和区别)
- 2024-09-18 Python | 面向对象如何快速实现(一)
- 2024-09-18 漫画:如何通俗易懂地解释面向对象思想?
- 2024-09-18 一文让你掌握Python面向对象的编程思维
- 2024-09-18 什么是面向对象,看这一篇就够了(什么叫面向对象)
- 2024-09-18 C#自学——面对对象(OOP)(c#面向对象的编程)
- 2024-09-18 面向对象:静态方法、类方法、属性方法
- 2024-09-18 Delphi基础教程图文版之初识面向对象
你 发表评论:
欢迎- 最近发表
- 标签列表
-
- 电脑显示器花屏 (79)
- 403 forbidden (65)
- linux怎么查看系统版本 (54)
- 补码运算 (63)
- 缓存服务器 (61)
- 定时重启 (59)
- plsql developer (73)
- 对话框打开时命令无法执行 (61)
- excel数据透视表 (72)
- oracle认证 (56)
- 网页不能复制 (84)
- photoshop外挂滤镜 (58)
- 网页无法复制粘贴 (55)
- vmware workstation 7 1 3 (78)
- jdk 64位下载 (65)
- phpstudy 2013 (66)
- 卡通形象生成 (55)
- psd模板免费下载 (67)
- shift (58)
- localhost打不开 (58)
- 检测代理服务器设置 (55)
- frequency (66)
- indesign教程 (55)
- 运行命令大全 (61)
- ping exe (64)
本文暂时没有评论,来添加一个吧(●'◡'●)