Python 为什么这个numpy数组太大而无法加载?

Python 为什么这个numpy数组太大而无法加载?,python,numpy,file-io,Python,Numpy,File Io,我有一个3.374Gb的npz文件,myfile.npz 我可以在中阅读并查看文件名: a = np.load('myfile.npz') a.files 给予 我能读懂“arr_1”行吗 a1=a['arr_1'] 但是,我无法加载arr_0,也无法读取其形状: a1=a['arr_0'] a['arr_0'].shape 上述两种操作都会导致以下错误: ValueError: array is too big 我有16Gb的RAM,其中8.370Gb可用。所以问题似乎与记忆无关。我的

我有一个3.374Gb的npz文件,
myfile.npz

我可以在中阅读并查看文件名:

a = np.load('myfile.npz')
a.files
给予

我能读懂“arr_1”行吗

a1=a['arr_1']
但是,我无法加载
arr_0
,也无法读取其形状:

a1=a['arr_0']
a['arr_0'].shape
上述两种操作都会导致以下错误:

ValueError: array is too big
我有16Gb的RAM,其中8.370Gb可用。所以问题似乎与记忆无关。我的问题是:

  • 我应该能够读入这个文件吗

  • 有人能解释这个错误吗

  • 我一直在考虑使用
    np.memmap
    来解决这个问题——这是一个合理的方法吗

  • 我应该使用什么调试方法

  • 编辑:


    我访问了一台内存更大(48GB)的计算机并加载了它。
    dtype
    实际上是
    complex128
    a['arr_0']
    的未压缩内存为5750784000字节。似乎可能需要RAM开销。要么是这一点,要么是我预测的可用RAM量是错误的(我使用的是WindowsSysInternalsRammap)

    一个
    np.complex128
    数组的维数
    (2001440,3,13,32)
    应该占用大约5.35GiB的未压缩空间,因此如果您确实有8.3GB的可用可寻址内存,那么原则上您应该能够加载该数组

    但是,根据您在下面评论中的回答,您使用的是32位版本的Python和numpy。在Windows中(如果二进制文件是使用
    IMAGE\u FILE\u LARGE\u ADDRESS\u AWARE
    标志编译的,则为4GB;大多数32位Python发行版不是这样)。因此,无论有多少物理内存,Python进程的地址空间都被限制为2GB

    您可以安装64位版本的Python、numpy和您需要的任何其他Python库,或者在2GB限制下生活并尝试解决它。在后一种情况下,您可以将超过2GB限制的阵列主要存储在磁盘上(例如,使用
    np.memmap
    ),但我建议您选择选项1,因为在大多数情况下,memmaped阵列上的操作要比完全驻留在RAM中的正常
    np.array
    慢得多


    如果您已经有了另一台具有足够RAM的机器,可以将整个阵列加载到核心内存中,那么我建议您以不同的格式保存阵列(可以是普通二进制,或者更好,使用or将其保存在HDF5文件中)。也可以从
    .npz
    文件中提取问题数组,而不将其加载到RAM中,这样您就可以将其作为驻留在磁盘上的
    np.memmap
    数组打开:

    import numpy as np
    
    # some random sparse (compressible) data
    x = np.random.RandomState(0).binomial(1, 0.25, (1000, 1000))
    
    # save it as a compressed .npz file
    np.savez_compressed('x_compressed.npz', x=x)
    
    # now load it as a numpy.lib.npyio.NpzFile object
    obj = np.load('x_compressed.npz')
    
    # contains a list of the stored arrays in the format '<name>.npy'
    namelist = obj.zip.namelist()
    
    # extract 'x.npy' into the current directory
    obj.zip.extract(namelist[0])
    
    # now we can open the array as a memmap
    x_memmap = np.load(namelist[0], mmap_mode='r+')
    
    # check that x and x_memmap are identical
    assert np.all(x == x_memmap[:])
    
    将numpy导入为np
    #一些随机稀疏(可压缩)数据
    x=np.随机.随机状态(0).二项式(1,0.25,(1000,1000))
    #将其另存为压缩的.npz文件
    np.savez_compressed('x_compressed.npz',x=x)
    #现在将其作为numpy.lib.npyio.NpzFile对象加载
    obj=np.load('x_compressed.npz')
    #包含格式为“.npy”的存储数组列表
    namelist=obj.zip.namelist()
    #将“x.npy”解压缩到当前目录中
    obj.zip.extract(名称列表[0])
    #现在我们可以将数组作为memmap打开
    x_memmap=np.load(名称列表[0],mmap_mode='r+'))
    #检查x和x_memmap是否相同
    断言np.all(x==x_memmap[:])
    
    我怀疑您无法加载它的原因是,例如,将3.4表示为计算机内存中的浮点值比将3.4保存在磁盘上需要更多的内存。但我比我开始阅读之前更不确定。你知道这个文件是不是被压缩的(是用什么方法创建的)?您是否在尝试加载它的同一台机器上创建了它?你知道它包含什么类型的数组(大小和数据类型)?@ali_m,是与
    np一起保存的。savez_compressed
    但是在另一台机器上。
    arru0
    是浮动(我认为是8字节)的
    (2001440,3,12,32)
    arru1
    是(200,3,32)再次浮动。尝试
    mmap\u mode='r'
    作为
    np.load
    的附加参数。这不应将阵列加载到内存中,而应将其保留在磁盘上。除非您随后将其复制到另一个数组。@Wicket对于包含多个数组的
    .npz
    文件无效(至少在我的计算机上)。当您实际尝试使用
    a['x']
    访问其中一个数组时,整个内容将作为标准
    np.array
    而不是
    np.memmap
    读取到内存中,无论您是否指定
    mmap\u模式=
    。我怀疑数组可能需要连续的虚拟内存空间,至少在某些方面是这样。我也可能是因为他使用的x32进程的地址空间限制为4GB。@atomh33ls您能确认您是在运行32位Windows,还是在其他方面限制为4GB的地址空间吗?您是否能够分配一个新的4GB numpy阵列(例如
    foo=np.ones(536870912,np.float64)
    )?@atomh33ls-Whelp,这是您的问题!要么安装64位版本的Python、numpy和任何其他需要的Python库,要么在可寻址内存的4GB限制下生活。谢谢@ali_m,我天真地认为操作系统只允许使用所有可用的RAM。另外,对于将来阅读的人来说,我发现它是有用的
    import numpy as np
    
    # some random sparse (compressible) data
    x = np.random.RandomState(0).binomial(1, 0.25, (1000, 1000))
    
    # save it as a compressed .npz file
    np.savez_compressed('x_compressed.npz', x=x)
    
    # now load it as a numpy.lib.npyio.NpzFile object
    obj = np.load('x_compressed.npz')
    
    # contains a list of the stored arrays in the format '<name>.npy'
    namelist = obj.zip.namelist()
    
    # extract 'x.npy' into the current directory
    obj.zip.extract(namelist[0])
    
    # now we can open the array as a memmap
    x_memmap = np.load(namelist[0], mmap_mode='r+')
    
    # check that x and x_memmap are identical
    assert np.all(x == x_memmap[:])