前言

单例模式是创建模式中比较常见和常用的模式,在程序执行的整个生命周期只存在一个实例对象。

系列文章

目录

简单理解

  • 每个类创建实例化对象的时候,保证在同一个上下文环境中确保某一个类只有一个实例,减少内存的开销。

python实现方法

python类的实例是由__new__方法创建的,因此单例要在new方法上做文章。

class Test(object):

    __instance = None

    def __new__(cls, *args, **kwargs):
if not cls.__instance:
cls.__instance=object.__new__(cls) # 将实例对象用一个变量引用住,以后每次创建时直接返回该对象
return cls.__instance def __init__(self):
pass class Test(object): __instance = None
__first_one = False def __new__(cls, *args, **kwargs):
if not cls.__instance:
cls.__instance=object.__new__(cls)
return cls.__instance def __init__(self, name):
if not self.__first_one: # 使用一个变量的状态来记录__init__的状态,保证只初始化一次,提高运行效率
self.__first_one = True
self.name = name

一般的应用场景

  • 创建对象时耗时过多或耗费资源过多,但又经常用到的对象;比如一个对象创建时有几十上百个属性需要初始化,而初始化参数又不变的;因为object._new_(cls)方法每执行一次就会在内存中创建一个新的实例。
class Test(object):

    __instance = None
__first_one = False def __new__(cls, *args, **kwargs):
if not cls.__instance:
cls.__instance=object.__new__(cls)
return cls.__instance def __init__(self, name):
if not self.__first_one: # 使用一个变量的状态来记录__init__的状态,保证只初始化一次,提高运行效率
self.__first_one = True
self.name1 = name
....
self.name100 = "xxxx"
  • 工具类对象;有时为了方便管理工具函数,会让工具函数变成某个类的实例方法,但是在调用的时候要先创建一个实例,所以这个实例可以是一个单例。

  • 频繁访问数据库或文件的对象;由于涉及io操作,耗时较多,所以良好的做法是在内存中维护一个连接池,需要的时候返回一个连接对象。

连接mysql实例

# 以连接mysql为例
from pymysql import * class MysqlManager(object):
pool = [] # 设置连接池
__instance = None
__first_one = False
count = 0 def __new__(cls, *args, **kwargs):
if not cls.__instance:
cls.__instance = object.__new__(cls)
return cls.__instance def __init__(self, host,port,database,user,password,charset='utf8',number=5):
if not self.__first_one:
self.__first_one = True
self.number = number
self.pool = [connect(host=host, port=port, database=database,
user=user, password=password, charset=charset) for i in range(number)] def __enter__(self): # 上下文管理器返回一个连接对象
if self.count < self.number:
con = self.pool[self.count]
self.count += 1
return con
else:
self.count = 0
return self.pool[0] def __exit__(self, exc_type, exc_val, exc_tb):
pass def get_cursor(self): # 直接得到一个游标
if self.count < self.number:
con = self.pool[self.count]
self.count += 1
return con.cursor()
else:
self.count = 0
return self.pool[0].cursor()
  • 多线程需要相同的创建的对象,可以使用单例共享资源优化配置。

总结

  1. python单例模式的实现原理主要是另__new__魔法方法和__init__魔法方法每次返回的对象不变即可;

  2. 单例模式主要用在当一些场景不关心实例的属性而只关系实例的方法,即业务需要使用对象的功能,对对象本身的属性不会去改变它。

参考

python设计模式之单例模式(一)的更多相关文章

  1. python设计模式之单例模式(二)

    上次我们简单了解了一下什么是单例模式,今天我们继续探究.上次的内容点这 python设计模式之单例模式(一) 上次们讨论的是GoF的单例设计模式,该模式是指:一个类有且只有一个对象.通常我们需要的是让 ...

  2. python设计模式之单例模式(转)

    设计模式之单例模式 单例设计模式是怎么来的?在面向对象的程序设计中,当业务并发量非常大时,那么就会出现重复创建相同的对象,每创建一个对象就会开辟一块内存空间,而这些对象其实是一模一样的,那么有没有办法 ...

  3. Python设计模式之单例模式

    1.由于语言的特性不同,设计模式的实现方式和实现难度也会不同 2.有的模式已经在语言内置了,比如迭代器模式. 3.单例模式可以直接用模块级变量来实现 4.普通工厂模式可以直接通过传入"类名& ...

  4. python设计模式之单例模式(一)

    单例设计模式的概念: 单例设计模式即确保类有且只有一个特定类型的对象,并提供全局访问点.一般我们操作数据库的时候为了避免统一资源产生互相冲突,创建单例模式可以维护数据的唯一性. 单例模式的特性: 确保 ...

  5. python设计模式之--单例模式

    python的单例模式就是一个类的实例只能自始自终自能创建一次.应用场景比如说数据库的连接池. #!/usr/bin/env python # coding=utf- class Foo(object ...

  6. Python设计模式中单例模式的实现及在Tornado中的应用

    单例模式的实现方式 将类实例绑定到类变量上 class Singleton(object): _instance = None def new(cls, *args): if not isinstan ...

  7. 【python 设计模式】单例模式

    单例模式(Singleton Pattern)是一种常用的软件设计模式,该模式的主要目的是确保某一个类只有一个实例存在.当你希望在整个系统中,某个类只能出现一个实例时,单例对象就能派上用场. 比如,某 ...

  8. python 设计模式之 单例模式

    单例模式是做为"全局变量"的替代品出现的.所以它具有全局变量的特点:全局可见.贯穿应用程序的整个生命期,保证在程序执行中,某个类仅仅存在一个实例,所以通常不希望类中的构造函数被调用 ...

  9. python 设计模式之单例模式 Singleton Pattern

    #引入 一个类被设计出来,就意味着它具有某种行为(方法),属性(成员变量).一般情况下,当我们想使用这个类时,会使用new 关键字,这时候jvm会帮我们构造一个该类的实例.这么做会比较耗费资源. 如果 ...

随机推荐

  1. (转)linux下压缩和归档相关命令tar,zip,gzip,bzip2

    压缩包也有两种形式,一种是tar.gz包(.tgz包也是这种),一种是tar.bz2包. tar.gz包的解压方法:tar zxvf [PackageName].tar.gz tar.bz2包的解压方 ...

  2. [HNOI/AHOI2018]排列 贪心

    题面 题解: 把题面的限制换成中文: 如果排在第k位的下标 = 排在第j位的值 ,那么k < j 换一个描述方式: 一个值为x的数要排在第x个数后面. 再换一个描述方式: \(fa[i] = a ...

  3. Java判断一个字符串str不为空:方法及时间效率

    判断一个字符串str不为空的方法有: 1.str == null; 2.”“.equals(str): 3.str.length <= 0; 4.str.isEmpty(): 注意:length ...

  4. Tajo--一个分布式数据仓库系统(概述)

    前言:一直对OS X比较仰慕,刚工作送给自己的第一件大礼就是mac pro,嘿嘿.最近在看一个叫tajo得分布式数据仓库,需要依赖protoc 2.4.1,2.5.0都不work,不知道为啥,我在装2 ...

  5. Linux内核分析第七周学习笔记——Linux内核如何装载和启动一个可执行程序

    Linux内核分析第七周学习笔记--Linux内核如何装载和启动一个可执行程序 zl + 原创作品转载请注明出处 + <Linux内核分析>MOOC课程http://mooc.study. ...

  6. 传说中的 SonarLint

    Sonar是一个用于代码质量管理的开源平台,用于管理源代码的质量 通过插件形式,可以支持包括java,C#,C/C++,PL/SQL,Cobol,JavaScrip,Groovy等等二十几种编程语言的 ...

  7. 只出现一次的数字 [ LeetCode ]

    给定一个非空整数数组,除了某个元素只出现一次以外,其余每个元素均出现两次.找出那个只出现了一次的元素. 说明: 你的算法应该具有线性时间复杂度. 你可以不使用额外空间来实现吗? 示例 1: 输入: [ ...

  8. #define _INTSIZEOF(n) ((sizeof(n)+sizeof(int)-1)&~(sizeof(int) - 1) )

    原文 功能: 首先,sizeof(int)肯定是2的次方数,比如32位是4,64位是8 ((sizeof(n)+sizeof(int)-1)&~(sizeof(int) - 1) ) 的意思就 ...

  9. Java 开发岗面试知识点

    本文作者在一年之内参加过多场面试,应聘岗位均为 Java 开发方向.在不断的面试中,分类总结了 Java 开发岗位面试中的一些知识点. 主要包括以下几个部分: Java 基础知识点 Java 常见集合 ...

  10. proxy vue3.0

    <html> <head> <meta charset="UTF-8" /> <meta name="viewport" ...