Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/282.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/sqlite/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 使用SQLite了解PonyORM中的内存消耗_Python_Sqlite_Memory Leaks_Orm_Ponyorm - Fatal编程技术网

Python 使用SQLite了解PonyORM中的内存消耗

Python 使用SQLite了解PonyORM中的内存消耗,python,sqlite,memory-leaks,orm,ponyorm,Python,Sqlite,Memory Leaks,Orm,Ponyorm,我有以下代码将一个大型CSV文件(超过350万行)加载到SQLite数据库中 该程序工作正常,但似乎没有释放内存,因此在运行该程序时,我可以通过命令top看到其内存大小如何增长,直到耗尽所有可用的服务器内存,并且在不插入所有行的情况下终止该程序 我的理解是,包含的db.commit()(每次我们开始在CSV中加载一个新的月份时都会执行)将释放创建的任何烛台实例(我认为,这些实例是导致内存增长的实例),但它不会这样做 为什么会发生这种情况,代码中有什么可以纠正的,以使其在没有内存泄漏的情况下工作

我有以下代码将一个大型CSV文件(超过350万行)加载到SQLite数据库中

该程序工作正常,但似乎没有释放内存,因此在运行该程序时,我可以通过命令
top
看到其内存大小如何增长,直到耗尽所有可用的服务器内存,并且在不插入所有行的情况下终止该程序

我的理解是,包含的
db.commit()
(每次我们开始在CSV中加载一个新的月份时都会执行)将释放创建的任何烛台实例(我认为,这些实例是导致内存增长的实例),但它不会这样做

为什么会发生这种情况,代码中有什么可以纠正的,以使其在没有内存泄漏的情况下工作

#-*-编码:utf-8-*-
#将CSV数据加载到SQLite数据库中
从十进制输入*
从日期时间导入日期时间
从pytz导入时区
从小马进口*
导入csv
#输入参数
csv_文件名='dax-1m.csv'
csv_时间范围='1m'
csv_分隔符=';'
csv“u quotechar=”
csv\u时区=时区(“美国/纽约”)
db_filename='dax.db'
db_时区=时区(“欧洲/柏林”)
#打开/创建数据库
db=数据库()
#数据模型
类烛台(db.Entity):
时间框架=必需(unicode)
时间戳=必需(日期时间)
打开=必需(十进制,精度=12,刻度=6)
高=必需(十进制,精度=12,刻度=6)
低=必需(十进制,精度=12,刻度=6)
关闭=必需(十进制,精度=12,刻度=6)
体积=所需(十进制,精度=12,刻度=6)
bind(provider='sqlite',filename=db\u filename,create\u db=True)
db.generate_映射(create_tables=True)
#装载机等级
类加载器():
def加载(自):
行数=0;
本年度=-1;
本月=-1;
打开(csv_文件名,换行符=“”)作为csvfile:
r=csv.reader(csvfile,delimiter=csv_delimiter,quotechar=csv_quotechar)
使用db_会话:
对于r中的行:
_年份=整数(第[0][4]行)
_月份=整数(第[0][3:-5]行)
_day=int(第[0][:2]行)
_小时=整数(第[1][:2]行)
_分钟=整数(第[1][3:5]行)
csv\u dt=日期时间(年、月、日、小时、分钟)
db_dt=csv_时区。本地化(csv_dt)。像散区(db_时区)
烛台(
timeframe=db_timezone.zone,
时间戳=db_dt,
打开=第[2]行,
高=第[3]行,
低=第[4]行,
关闭=第[5]行,
体积=第[6]行
)
行计数+=1
如果(\u年!=当前年或\u月!=当前月):
db.commit()
本年度=\u年度
当前月份=\u月份
打印('+str(当前年)+'+str(当前月)+'..的加载数据)
打印('已加载'+str(行计数)+'寄存器')
ldr=Loader()
ldr.load();

此处没有内存泄漏。小马在离开db_会话作用域时清除缓存 在这里你可以看到更多关于这个的信息

特别是这个:

会话结束时,将执行以下操作:

  • 清除标识映射缓存
您需要缩小db_会话的范围。 另一个选项是在N个对象创建之后执行commit(),然后执行rollback()以清除缓存:

with db_session(strict=True):
    for i, row in enumerate(r):
        <do some work>
        if i % 10000 == 0:
            commit()  # save the changes
            rollback()  # clear the cache
具有db_会话的
(strict=True):
对于i,枚举(r)中的行:
如果i%10000==0:
提交()#保存更改
回滚()#清除缓存
有关回滚()的详细信息,请参见此处: