Python列表类型结构中合理地存储10亿及以上值

3
我正在编写一个程序,用于为转换为数组的数字高程模型的固定区域创建各种功能图。我计算窗口限制内点对之间的方差(高度差异)和滞后(距离)。每个数组位置都与其他数组位置进行比较。对于每一对,滞后和方差值被追加到不同的列表中。一旦所有配对完成,就会使用这些列表进行数据分组、平均化和最终绘图。
针对较小的窗口大小(比如60x60像素),程序运行良好。对于120x120像素左右的窗口,我能够缓慢地让程序运行。如果超过这个大小,我会遇到"MemoryError"错误报告-例如,对于240x240像素的区域,我将有3,317,760,000个条目。
在程序开始时,我创建了一个空列表:
variance = []
lag =  []

接着在 for 循环中,我计算滞后和方差,并将这些值添加到不同的列表中:

variance.append(var_val)
lag.append(lag_val)

我已经查看了stackoverflow页面,并发现有一个类似的问题在这里进行讨论。该解决方案可能会提高程序的暂时性能,但是所提供的解决方案只适用于100万个条目,因此对于较大区域(例如240x240像素)无济于事。我还考虑使用numpy数组来存储值,但我不认为这可以避免内存问题。
如果您有任何建议,希望能提供一些使用我定义的较大窗口大小的列表的方法。
由于我刚学习Python,请原谅我的无知。
主要代码的大部分内容可以在这里看到。

3
不用担心内存需求;由于比较数量呈指数增长,你的算法在处理更大数据集时似乎永远也无法完成。 - Martijn Pieters
1
你应该使用numpy数组而不是列表(虽然不能解决你的问题,但速度会更快)。你的克里金代码的其余部分是什么样子的?我猜你在那里也会遇到问题。 - usethedeathstar
1
@MartijnPieters:是二次方的,但不是指数级增长的 :-) - Armin Rigo
1
在我看来,你应该考虑彻底改变你的方法。与其计算一系列方差和滞后,然后再计算诸如区间等摘要统计量,不如在进行计算时就同时计算这些摘要统计量。这样,你的最大内存需求将是你运行摘要统计量的大小。 - TooTone
1
@TooTone 一个新的方法正是我所需要的——除了用于汇总统计信息的列表外,我的代码中再也没有其他列表了——这些统计信息确实是在我进行计算时得出的。为了减少运行时间,我选择了一种随机抽样策略,而不是将窗口内的所有像素相互比较。 - ChrisWills
显示剩余6条评论
3个回答

0
使用Python的array模块。它提供了一些类似于列表的类型,这些类型更节省内存(但不能用于存储随机对象,不像常规列表)。例如,您可以有包含常规浮点数(C术语中的“双精度”)甚至是单精度浮点数(每个四个字节而不是八个字节,代价是降低精度)的数组。 30亿个这样的单精度浮点数的数组将适合12 GB的内存中。

0
你可以考虑使用PyTables,它是一个库,封装了HDF5 C库,可与numpy和pandas一起使用。
基本上,PyTables会将您的数据存储在磁盘上,并在需要时透明地将其加载到内存中。
或者,如果您想坚持使用纯Python,可以使用sqlite3数据库来存储和操作数据-文档中说sqlite数据库的大小限制为140TB,这应该足够存储您的数据。

0
尝试使用heapq,导入heapq。它使用堆进行存储,而不是栈,使您可以访问计算机的全部内存。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接