使用__slots__节省python内存技巧
__slots__作用
__slots__有一个作用是:限制类实例绑定的属性,但是它有一个更重要的作用就是节省内存,当然更适用于数据量大的情况(万量级以上)。
__slots__节省内存的原理
class Measurement:
def __init__(self, x, y, value):
self.x = x
self.y = y
self.val = value
m1 = Measurement(1, 2, "Happy")
m2 = Measurement(7, 10, "Crazy")
m2.other = True
其实,对类的变量值进行初始化,底层是通过一个指针指向__dict__(里面包含潜在的字段名和字段值)。举个例子,上面的程序底层实现过程如下:

我们也可以通过程序查看这一底层形式:
```
print(m1.__dict__) # {'x': 1, 'y': 2, 'val': 'Happy'}
print(m2.__dict__) # {'x': 7, 'y': 10, 'other': True, 'val': 'Crazy'}
```
这就是python自定义变量底层的一个基本实现。通过对这一底层理解,我们就会知道,如果我们的实例有数百万个,那么底层会有相应数百万个字典拥有相同的key值(知识value值不同),这时非常耗内存的,这时候__slots__就发挥它的作用了。
通过__slots__,我们可以稍微调整一下类,以改变类中字段的存储方式,废弃原来那种耗费内存的1对1重复的字典分配方式。具体如下:
class Measurement:
__slots__ = ['x', 'y', 'val']
def __init__(self, x, y, value):
self.x = x
self.y = y
self.val = value
这样我们底层的实现就会变为如下方式:

我们可以看出,现在字段名是与Measurement类这个类型相关联,而不是原来的与相应的实例1对1的关联。而字段值与原来的方式无差别,因为毕竟各个实例的字段名一样,可以统一存放,而字段值并不都是一样,当然对于字段值也一样的我们也统一存储(因为底层字典都是与类这个类型关联,而不是与每个实例的__dict__关联)。但对于数据量庞大的情况(数百万级以上),能够非常显著的节省内存空间(25.5GB -> 16.2GB)。
以上就是__slots__能够节省内存的原理,主要还是要搞清楚python的类变量初始化的底层操作是通过字典存储后相关联这一方式进行的,__slots__只是改变了字典key,value与实例相关联的方式,可以总结如下:
默认变量实例化方法:底层实例和字典是一对一的关系
加入__slots__后:底层实例和字典是多对一的关系(重复的部分)。
使用__slots__节省python内存技巧的更多相关文章
- 填坑总结:python内存泄漏排查小技巧
摘要:最近服务遇到了内存泄漏问题,运维同学紧急呼叫解决,于是在解决问题之余也系统记录了下内存泄漏问题的常见解决思路. 本文分享自华为云社区<python内存泄漏排查小技巧>,作者:luti ...
- Python内存优化
实际项目中,pythoner更加关注的是Python的性能问题,之前也写过一篇文章<Python性能优化>介绍Python性能优化的一些方法.而本文,关注的是Python的内存优化,一般说 ...
- Python内存优化:Profile,slots,compact dict
实际项目中,pythoner更加关注的是Python的性能问题,之前也写过一篇文章<Python性能优化>介绍Python性能优化的一些方法.而本文,关注的是Python的内存优化,一般说 ...
- Python内存管理机制及优化简析(转载)
from:http://kkpattern.github.io/2015/06/20/python-memory-optimization-zh.html 准备工作 为了方便解释Python的内存管理 ...
- 记一次调试python内存泄露的问题
转载:http://www.jianshu.com/p/2d06a1a01cc3 这两天由于公司需要, 自己编写了一个用于接收dicom文件(医学图像文件)的server. 经过各种coding-de ...
- Python内存分配器(如何产生一个对象的过程)
目录 内存分配器 Python分配器分层 第零层--通用的基础分配器 第一层--低级内存分配器 内存结构 arena pool new arena usable_arenas和unused_arena ...
- 【python测试开发栈】—python内存管理机制(二)—垃圾回收
在上一篇文章中(python 内存管理机制-引用计数)中,我们介绍了python内存管理机制中的引用计数,python正是通过它来有效的管理内存.今天来介绍python的垃圾回收,其主要策略是引用计数 ...
- python实用技巧之任务切分
Python 大任务切分小任务 今天来说说,Python中的任务切分.以爬虫为例,从一个存 url 的 txt 文件中,读取其内容,我们会获取一个 url 列表.我们把这一个 url 列表称为大任务. ...
- python内存管理(通俗易懂,详细可靠)
python内存管理 python3.6.9 内存管理的官方文档 https://docs.python.org/zh-cn/3.6/c-api/memory.html 一.变量存哪了? x = 10 ...
随机推荐
- A New Function(LightOJ 1098)积性函数前缀和的应用
题意:要求对于1~n,每个数的约数(不包括1和其本身)的和. 题解:由于题目数据有2*10^9之大,因而不能直接暴力.需要考虑积性函数的特性,由于必定有重复的约数出现,因而可以对重复约数所在的区间进行 ...
- Selenium - 搭建环境
1. 在Python中安装第三方库 1)安装Selenium 通过pip安装 2). 下载geckodriverckod 从selenium3开始,webdriver/firefox/webdri ...
- best practices for designing web api
restful why: meaningful This will be improve efficiency , less documents , just read the code auto g ...
- 使用fpm 软件包打包
安装 sudo gem install --no-ri --no-rdoc fpm 简单使用 一个 redis的简单demo % ls src/redis-server redis.conf src/ ...
- Dynamics CRM Instances
Dynamics CRM 的instances: 当我们打开Dynamics 365 admin portal 会看到我们instance是什么: 新 admin center界面: 当前的admin ...
- 将string转为同名类名,方法名。(c#反射)
using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace stri ...
- npm镜像地址的修改或切换
方法一:直接编辑npm的配置文件npm config edit修改registry的地址registry=https://registry.npm.taobao.org 方法二:用代码更改npm的配置 ...
- 从零开始实现RPC框架 - RPC原理及实现
最近被人问到RPC相关的东西~突然发现还是有很多原理没有清楚,所以要好好系统的学习一下RPC以及它的原理 先大致了解一下RPC的大概,原文:https://blog.csdn.net/top_code ...
- window.open() 打开的子页面 往主页面传参问题
<!--主页面的代码--><!DOCTYPE html> <html> <head> <meta charset="utf-8" ...
- TCARS: Time- and Community-Aware Recommendation System(时间感知和社区感知推荐系统)
随着用户在物品上产生了大量行为,推荐系统成为了线上系统的重要组成部分.推荐系统算法使用用户对物品的行为信息以及上下文数据为每个用户推荐一组物品.算法根据用户之间及物品之间的相似度建立.本文介绍了一个基 ...