3

我正在使用numpy ndarray's 将大型 h5 文件加载到内存中。我读到我的系统(Win 7 prof.,6 GB RAM)应该允许 python.exe 使用大约 2 GB 的物理内存。

但是,我MemoryError已经接近 1 GB。更奇怪的是,这个下限似乎只适用于numpy array's 而不是适用于 a list

我已经使用此处找到的以下函数测试了我的内存消耗:

import psutil
import gc
import os
import numpy as np
from matplotlib.pyplot import pause

def memory_usage_psutil():
    # return the memory usage in MB
    process = psutil.Process(os.getpid())
    mem = process.get_memory_info()[0]/float(2**20)
    return mem

测试 1:测试普通列表的内存限制

print 'Memory - %d MB' %memory_usage_psutil() # prints memory usage after imports
a = []
while 1:
    try:
        a.append([x*2000 for x in xrange(10000)])
    except MemoryError:
        print 'Memory - %d MB' %memory_usage_psutil()
        a = []
        print 'Memory - %d MB' %memory_usage_psutil()
        print 'run garbage collector: collected %d objects.' %gc.collect()
        print 'Memory - %d MB\n\n' %memory_usage_psutil()
        break

测试 1 打印:

Memory - 39 MB
Memory - 1947 MB
Memory - 1516 MB
run garbage collector: collected 0 objects.
Memory - 49 MB

测试 2:创建多个大型np.array's

shape = (5500,5500)
names = ['b', 'c', 'd', 'g', 'h']

try:
    for n in names:
        globals()[n] = np.ones(shape, dtype='float64')
        print 'created variable %s with %0.2f MB'\
        %(n,(globals()[n].nbytes/2.**20))
except MemoryError:
    print 'MemoryError, Memory - %d MB. Deleting files..'\
    %memory_usage_psutil()
    pause(2)
    # Just added the pause here to be able to observe
    # the spike of memory in the Windows task manager.
    for n in names:
        globals()[n] = []
    print 'Memory - %d MB' %memory_usage_psutil()
    print 'run garbage collector: collected %d objects.' %gc.collect()
    print 'Memory - %d MB' %memory_usage_psutil()

测试 2 打印:

Memory - 39 MB
created variable b with 230.79 MB
created variable c with 230.79 MB
created variable d with 230.79 MB
created variable g with 230.79 MB
MemoryError, Memory - 964 MB. Deleting files..
Memory - 39 MB
run garbage collector: collected 0 objects.
Memory - 39 MB

我的问题:为什么我在接近 2GB 限制之前就得到了 a ,为什么 a和MemoryError的内存限制有差异,或者我错过了什么?我正在使用 python 2.7 和 numpy 1.7.1listnp.array

4

1 回答 1

2

这可能是因为 numpy 数组正在使用一些 C 数组库(为了速度),即调用 malloc 的地方。然后这会失败,因为它无法分配连续的1GB 内存。我进一步猜测 Python 列表是作为链表实现的,因此列表所需的内存不需要是连续的。因此,如果您有足够的可用内存但它是碎片化的,那么您的数组 malloc 将失败,但您的链表将允许您使用所有不连​​续的部分。

于 2013-10-04T00:25:10.133 回答