正在寫python單例模式的一些東西,查到資料,記錄一下。原文地址:http://hi.baidu.com/tianfeng1015/blog/item/f0373dd0fbb8bbcb50da4bca.htmlhtml
咱們能夠使用 __new__ 這個特殊方法。該方法能夠建立一個其所在類的子類的對象。更可喜的是,咱們的內置 object 基類實現了 __new__ 方法,因此咱們只需讓 Sing 類繼承 object 類,就能夠利用 object 的 __new__ 方法來建立 Sing 對象了。python
- class Sing(object):
- def __init__():
- "disable the __init__ method"
- __inst = None # make it so-called private
- @staticmethod
- def getInst():
- if not Sing.__inst:
- Sing.__inst = object.__new__(Sing)
- return Sing.__inst
如今咱們只能經過 Sing.getInst() 來建立 Sing 對象了。並且咱們也讓類屬性 __inst 保持了私有(雖然在 Python 中仍是有辦法訪問)。那麼,這是否意味着基本沒有問題了?固然不是!咱們還應該解決一個最關鍵的多線程問題。
同時,咱們應該還注意到,因爲咱們禁用了 __init__ 方法(顯式定義了它),咱們就應該顯式的調用其基類的 __init__ 方法(或許這裏的 object 類對於咱們無關痛癢),以做完整的初始化。固然,這個顯式的調用也應該移到 getInst() 中去了。多線程
- import threading
- class Sing(object):
- def __init__():
- "disable the __init__ method"
- __inst = None # make it so-called private
- __lock = threading.Lock() # used to synchronize code
- @staticmethod
- def getInst():
- Sing.__lock.acquire()
- if not Sing.__inst:
- Sing.__inst = object.__new__(Sing)
- object.__init__(Sing.__inst)
- Sing.__lock.release()
- return Sing.__inst
上面的代碼中,Sing.__lock.acquire() 和 Sing.__lock.release() 之間的是同步區域,它保證了對象建立的惟一性。同時,object 的 __init__ 方法調用僅僅置於 if 塊中,由於它和 Sing 實例同樣僅需初始化一次。好了,如今咱們的 Singleton 模式應該是基本完善了。ide