Python——单例模式的实现、pickle序列化模块

Python——单例模式的实现、pickle序列化模块

单例模式概述

单例模式的概述:

	单例模式是一种常用的软件设计模式。在它的核心结构中只包含一个被称为单例类的特殊类。通过单例模式可以保证系统中一个类只有一个实例而且该实例易于外界访问,从而方便对实例个数的控制并节约系统资源。如果希望在系统中某个类的对象只能存在一个,单例模式是最好的解决方案。

	单例模式的要点有三个;一是某个类只能有一个实例;二是它必须自行创建这个实例;三是它必须自行向整个系统提供这个实例。

	从具体实现角度来说,就是以下三点:一是单例模式的类只提供私有的构造函数,二是类定义中含有一个该类的静态私有对象,三是该类提供了一个静态的共有函数用于创建或获取它本身的静态私有对象。

单例模式应用

应用

一些资源管理器常常设计成单例模式

在计算机系统中,需要管理的资源包括软件外部资源,譬如每台计算机可以有若干个打印机,但只能有一个Printer Spooler,以避免两个打印机作业同时输出到打印机中。每台计算机可以有若干传真机卡,但是只应该有一个软件负责管理传真卡,以避免一个通信端口同时被两个请求同时调用。

需要管理的资源包括软件内部资源,譬如,大多数的软件都有一个(甚至多个)属性(properties)文件存放系统配置。这样的系统应当由一个对象来管理一个属性文件。

需要管理的软件内部资源也包括负责记录网站来访人数的部件,记录软件系统内部事件、出错信息的部件,或是对系统的表现进行检查的部件等。其一,这些资源管理器构件必须只有一个实例;其二,它们必须自行初始化;其三,允许整个系统访问自己。因此,它们都满足单例模式的条件,是单例模式的应用。

单例模式优缺点

单例模式的优缺点:

优点:

1、实例控制

单例模式会阻止其他对象实例化其自己的单例对象的副本,从而确保所有对象都访问唯一实例。

2、灵活性

因为类控制了实例化过程,所以类可以灵活更改实例化过程。

缺点:

1、开销

虽然数量很少,但如果每次对象请求引用时都要检查是否存在类的实例,将仍然需要一些开销。可以通过使用静态初始化解决此问题。

2、可能的开发混淆

使用单例对象(尤其在类库中定义的对象)时,开发人员必须记住自己不能使用new关键字实例化对象。因为可能无法访问库源代码,因此应用程序开发人员可能会意外发现自己无法直接实例化此类。

3、对象生成期

不能解决删除单个对象的问题。在提供内存管理的语言中(例如基于.NET Framework的语言),只有单例类能够导致单例类中出现悬浮引用。

单例模式实现的多种方式

'''
# # coding:utf-8
# 通过__new__方法实现
class SingleDemo:
    def __new__(cls, *args, **kwargs):
        if not hasattr(cls, 'instance'):
            cls._instance = super(SingleDemo, cls).__new__(cls)
        return cls._instance

    def __init__(self):
        print('__init__执行了')
obj = SingleDemo()
print(obj.__dict__)
print(id(obj))

# # 通过使用类实现
# class SingleDemo1(object):
#     # 静态变量
#     _instance = None
#     _flag = False
#     def __new__(cls, *args, **kwargs):
#         if cls._instance is None:
#             cls._instance = super().__new__(cls)
#         return cls._instance
#
#     def __init__(self):
#         if not SingleDemo1._flag:
#             SingleDemo1._flag = True
#
# obj1 = SingleDemo1()
# print(obj.__dict__)
# print(id(obj))
#
#
# 通过装饰器实现
def singleton(cls):
    # 创建一个字典用来保存类的示例对象
    instance = {}
    def inner(*args, **kwargs):
        # 先判断这个类有没有对象
        if cls not in instance:
            instance[cls] = cls(*args, **kwargs)
        return instance[cls]
    return inner

@singleton
class SingerDemo2(object):
    a = 1
    def __init__(self, x=0):
        self.x = x
#
#
# obj3 = SingerDemo2(1)
# obj4 = SingerDemo2(2)
# print(obj3.__dict__)
# print(obj4.__dict__)
# print(id(obj3))
# print(id(obj4))

# 单例模式  __new__实现
class Singleton:
    _instance = None
    _flag = False

    def __init__(self):
        if not Singleton._flag:
            print('__init__执行了')
            Singleton._flag = True

    def __new__(cls, *args, **kwargs):
        # print('__new__执行了')
        if not Singleton._instance:
            print('__new__执行了')
            cls._instance = super().__new__(cls)
        return cls._instance


obj = Singleton()
print(obj)
obj1 = Singleton()
print(obj1)


'''

pickle序列化模块

'''
优势:能够序列化python中所有的类型
缺陷:只能够在python中使用 无法跨语言传输 
 
需求:产生一个对象并保存到文件中 取出来还是一个对象
'''
# coding:utf-8
import pickle
class Demo:
    def __init__(self, name, age):
        self.name = name
        self.age = age

    def func(self):
        print('from func')

    def func1(self):
        print('from func1')

obj = Demo('jason', 28)

with open(r'a.txt', 'wb') as f:
    pickle.dump(obj, f)

with open(r'a.txt', 'rb') as f:
    data = pickle.load(f)

print(data)  # <__main__.Demo object at 0x000001C693A1BE50>
data.func()  # from func
data.func1()  # from func1
print(data.name)  # jason
posted @ 2022-11-09 14:55  负剑远游行归来仍少年  阅读(59)  评论(0)    收藏  举报