专业编程教程与实战项目分享平台

网站首页 > 技术文章 正文

设计模式与面向对象

ins518 2024-09-11 09:28:43 技术文章 21 ℃ 0 评论

一、设计模式

设计模式:对软件设计中普遍存在(反复出现)的各种问题,所提出的解决方案。

每一个设计模式系统地命名、解释和评价了面向对象系统中一个重要的和重复出现的设计。

设计模式的创始人,一般称为“四人帮”(Gang of Four, GoF):Erich Gamma,Richard Helm,Ralph Johnson,John Vlissides......他们编写一套书来介绍23种设计模式:《设计模式:可复用面向对象软件的基础》。


二、面向对象回顾

设计模式是用来设计面向对象系统中的设计。不解决面向过程的问题。

1、面向对象的三大特性

封装:把数据和函数封装到一个类里,体现类内和类外。

继承:由于有了封装,需要通过继承在类之间复用代码。

多态:python本身是一门多态语言,因此不需去处理多态的问题。Java中则会区分虚类和普通类。

因此这三个特性是一个递进的关系。

2、接口

接口:若干抽象方法的集合。

作用:限制实现接口类必须按照接口给定的调用方式实现这些方法;对高层模块隐藏了类的内部实现

# 方法一:继承
# 存在的问题是:如果不调用pay方法并不会报错
class Payment:
 def pay(self, money):
 raise NotImplementedError
class Alipay(Payment):
 pass
class WechatPay(Payment):
 pass
p = Alipay()
p.pay(100)
# 方法二:抽象类
# 约束子类必须实现抽象类:TypeError: Can't instantiate abstract class Alipay with abstract methods pay
from abc import ABCMeta, abstractmethod
class Payment(metaclass=ABCMeta):
 # abstract class
 @abstractmethod
 def pay(self, money): # 抽象方法
 pass
class Alipay(Payment):
 def pay(self, money): # 实现Payment接口
 print('支付宝支付%d元' % money)
class WechatPay(Payment):
 def pay(self, money): # 实现Payment接口
 print("微信支付%d元" % money)
p = Alipay()
p.pay(100)

不用去查看具体实现,只要去查看接口(抽象类)的结构和注释,就可以了解需要传递的参数和pay方法的使用。

在写底层模块或者开源框架时需要大量应用设计模式,优化封装,让程序员在学习和使用时非常方便。


三、面向对象设计SOLID原则

不管是面向对象设计还是各个设计模式都需要遵循这五大原则。

  • 开放封闭原则:一个软件实体如类、模块和函数应该对扩展开放,对修改关闭。即软件实体应尽量在不修改原有代码的情况下进行扩展。
  • 里氏替换原则:所有引用父类的地方必须能透明地使用其子类的对象。(子类是特殊的父类,子类继承父类时同样方法的表现一致)
# 子类和父类的show_name内部实现和逻辑可能不同,但是参数和返回值是相同的
class User:
 def show_name(self):
 pass
class VIPUser(User):
 def show_name(self):
 pass
def show_user(u): # u可以是普通用户或VIP
 res = u.show_name()
  • 依赖倒置原则:高层模块不应该依赖低层模块,二者都应该依赖其抽象;抽象不应该依赖细节;细节应该依赖抽象。换言之,要针对接口编程,而不是针对实现编程。
from abc import ABCMeta, abstractmethod
class Payment(metaclass=ABCMeta): # 抽象
 # abstract class
 @abstractmethod
 def pay(self, money): # 抽象方法
 pass
class Alipay(Payment): # 细节
 def pay(self, money): # 实现Payment接口
 print('支付宝支付%d元' % money)
class WechatPay(Payment): # 细节
 def pay(self, money): # 实现Payment接口
 print("微信支付%d元" % money)
  • 接口隔离原则:使用多个专门的接口,而不使用单一的总接口,即客户端不应该依赖那些它不需要的接口。
from abc import ABCMeta, abstractmethod
# (一)单一总接口的情况
# 子类必须实现所有抽象方法,但其实很多方法是子类不需要的
class Animal(metaclass=ABCMeta):
 @abstractmethod
 def walk(self):
 pass
 @abstractmethod
 def swim(self):
 pass
 @abstractmethod
 def fly(self):
 pass
class Tiger(Animal): # Class Tiger must implement all abstract methods
 def walk(self):
 print("老虎走路")
# (二)多个接口隔离情况
class LandAnimal(metaclass=ABCMeta):
 @abstractmethod
 def walk(self):
 pass
class WaterAnimal(metaclass=ABCMeta):
 @abstractmethod
 def swim(self):
 pass
class SkyAnimal(metaclass=ABCMeta):
 @abstractmethod
 def fly(self):
 pass
class Tiger(LandAnimal):
 def walk(self):
 print("老虎走路")
class Frag(LandAnimal,WaterAnimal): # 青蛙多继承
 pass
  • 单一职责原则:不要存在多于一个导致类变更的原因。通俗的说,即一个类只负责一项职责。


四、设计模式分类

1、创建型模式(5种)

主要聚焦怎么去创建对象。目的是为了隐藏底层模块的逻辑。

工厂方法模式、抽象工厂模式、创建者模式、原型模式、单例模式。

创建型模式

2、结构型模式(7种)

主要关注在几个类之间怎么组合协同工作在一起。

适配器模式、桥模式、组合模式、装饰模式、外观模式、享元模式、代理模式。

结构型模式

3、行为型模式(11种)

主要关注方法和行为的完成。

解释器模式、责任链模式、命令模式、迭代器模式、中介者模式、备忘录模式、观察者模式、状态模式、策略模式、访问者模式、模板方法模式。

行为型模式


五、设计模式总结

python这门语言是一个动态语言,对参数、父类子类等限制不严格。对设计模式并不强求,不是完全契合,而java则是完全与设计模式契合。但是了解一些设计模式对写出优秀代码还是非常有帮助的。

在写大型项目时,尤其是底层代码、开源框架等时,设计模式的优势将更加突出。

有想学习前端或者转行的朋友欢迎私信小编“学习”加群,内有全套前端开发学习资料,欢迎加入

本文暂时没有评论,来添加一个吧(●'◡'●)

欢迎 发表评论:

最近发表
标签列表