1. 程式人生 > >(一)python 設計模式 --- 六大原則

(一)python 設計模式 --- 六大原則

單一職責原則(SRP:Single responsibility principle),一個類或者模組應該有且只有一個改變的原因,例如,搓衣板,既可以用來跪,也可以用來洗衣服。而在單一職責原理下,搓衣板的兩個功能就是引起這個類變化的兩個原因,就應該寫成兩個類

# -*- coding: utf-8 -*-

"""
單一職責原則
"""


class Person(object):

    """ 人類 """

    def duty(self, one):

        """ Coder 的職責是寫程式碼 ,農民就負責鬥地主,其餘的學習 """

        return
one is "Coder" and "Coding" or one is "Farmer" and "Chinese poker" or "Studying" if __name__ == '__main__': p = Person() print(p.duty("Coder"))
  • 此時如果細分責任到每一個人,豈不是一堆的判斷,肯定不科學,所以儘量讓一個類或者一個模組做一件事
# -*- coding: utf-8 -*-

"""
單一職責原則
"""


class Person(object):

    """ 人類 """

    def
duty(self, one):
""" Coder 的職責是寫程式碼 ,農民就負責鬥地主,其餘的學習 """ return one is "Coder" and "Coding" or one is "Farmer" and "Chinese poker" or "Studying" class Coder(Person): """ 農民 """ def duty(self): """ Coder 的職責是寫程式碼 """ return "Coding" class Farmer(Person)
:
""" 程式設計師 """ def duty(self): """ 農民就負責鬥地主 """ return "Chinese poker" if __name__ == '__main__': c = Coder() print(c.duty()) f = Farmer() print(f.duty())

里氏替換原則( LSP:Liskov Substitution Principle):任何基類可以出現的地方,子類一定可以出現。 LSP是繼承複用的基石,只有當衍生類可以替換掉基類,軟體單位的功能不受到影響時,基類才能真正被複用,而衍生類也能夠在基類的基礎上增加新的行為

  • 子類必須完全實現父類的抽象方法,但不能覆蓋父類的非抽象方法

  • 子類可以實現自己特有的方法

  • 當子類覆蓋或實現父類的方法時,方法的前置條件(即方法的形參)要比父類方法的輸入引數更寬鬆。

  • 當子類的方法實現父類的抽象方法時,方法的後置條件(即方法的返回值)要比父類更嚴格。

  • 子類的例項可以替代任何父類的例項,但反之不成立

# -*- coding: utf-8 -*-
import abc
import time
"""
里氏替換原則
"""
HOUR = 3600

class Person(object):

    """ 人類 """
    @abc.abstractmethod
    def duty(self):

        """ 職責 """
        pass


class Coder(Person):

    """ 程式設計師 """

    def duty(self):

        """ Coder 的職責是寫程式碼 """

        return "Coding"

    def sleep(self):

        """ 有時睡5小時 """

        time.sleep(5*HOUR)


class Farmer(Person):

    """ 程式設計師 """

    def duty(self):

        """ 農民就負責鬥地主 """

        return "Chinese poker"

    def sleep(self):

        """ 農民可以睡八小時 """

        time.sleep(8*HOUR)

依賴倒置原則(Dependence Inversion Principle):高層模組不應該依賴低層模組,二者都應該依賴其抽象;抽象不應該依賴細節;細節應該依賴抽象

# -*- coding: utf-8 -*-
import abc
import time
"""
里氏替換原則
"""
HOUR = 3600

class Person(object):

    """ 人類 """
    @abc.abstractmethod
    def duty(self):

        """ 職責 """
        pass


class Coder(Person):

    """ 程式設計師 """

    def duty(self):

        """ Coder 的職責是寫程式碼 """

        return "Coding"

    def sleep(self):

        """ 睡5小時 """

        time.sleep(5*HOUR)

介面隔離原則(Interface Segregation Principle) 這個原則的意思是:每個介面中不存在子類用不到卻必須實現的方法,如果不然就要將介面拆分,使用多個隔離的介面,比使用單個介面(多個介面方法集合到一個介面)要好

# -*- coding: utf-8 -*-
"""
介面隔離原則
"""
import abc
import time
import types

HOUR = 3600

class Person(object):

    """ 人類 """
    @abc.abstractmethod
    def duty(self):

        """ 職責 """
        pass


class Coder(Person):

    """ 程式設計師 """

    def duty(self):

        """ Coder 的職責是寫程式碼 """

        return "Coding"

    def sleep(self):

        """ 有時睡5小時 """

        time.sleep(5*HOUR)

# 方法一
# def programme(self, language='Php'):
#     """ 例項動態方法 """
#     return language

# 方法二
# @classmethod
# def programme(cls, language='Php'):
#     """ 類動態方法 """
#     return language

# 方法三
@staticmethod
def programme(language='Php'):
    """ 靜態方法 """
    return language

if __name__ == '__main__':

    # 方法一:給例項繫結方法
    # p = Coder()
    # p.programme = types.MethodType(programme, p)
    # print(p.programme('Python'))

    # 方法二:
    # p = Coder()
    # Coder.programme = programme
    # print(Coder.programme('Java'))
    # print(p.duty())

    # 方法三:靜態方法
    p = Coder()
    Coder.programme = programme
    print(Coder.programme('Java'))
    print(p.programme('Golang'))
    print(p.duty())

迪米特原則: 一個物件應該對其他物件保持最少的瞭解。

  • 問題由來:類與類之間的關係越密切,耦合度越大,當一個類發生改變時,對另一個類的影響也越大。

  • 解決方案:儘量降低類與類之間的耦合。

  • 軟體程式設計的總的原則:低耦合,高內聚。無論是面向過程程式設計還是面向物件程式設計,只有使各個模組之間的耦合儘量的低,才能提高程式碼的複用率。低耦合的優點不言而喻,要做到低耦合,正是迪米特法則要去完成的。

  • 迪米特法則又叫最少知道原則,最早是在1987年由美國Northeastern University的Ian Holland提出。通俗的來講,就是一個類對自己依賴的類知道的越少越好。也就是說,對於被依賴的類來說,無論邏輯多麼複雜,都儘量地的將邏輯封裝在類的內部,對外除了提供的公共方法,不對外洩漏任何資訊。迪米特法則還有一個更簡單的定義:只與直接的朋友通訊。首先來解釋一下什麼是直接的朋友:每個物件都會與其他物件有耦合關係,只要兩個物件之間有耦合關係,我們就說這兩個物件之間是朋友關係。耦合的方式很多,依賴、關聯、組合、聚合等。其中,我們稱出現成員變數、方法引數、方法返回值中的類為直接的朋友,而出現在區域性變數中的類則不是直接的朋友。也就是說,陌生的類最好不要作為區域性變數的形式出現在類的內部。

開閉原則:一個軟體實體如類、模組和函式應該對擴充套件開放,對修改關閉

  • 不要改你以前寫的程式碼,你應該加一些程式碼去擴充套件原來的功能,來實現新的需求。好處很好理解,改原來的程式碼很容易影響原來的功能,特別是接手別人的程式碼,不理解原先業務場景的情況下。