我正在使用Python的多处理函数在具有大约500GB RAM的机器上并行运行我的代码。为了在不同的工作线程之间共享一些数组,我正在创建一个Array
对象:
N = 150
ndata = 10000
sigma = 3
ddim = 3
shared_data_base = multiprocessing.Array(ctypes.c_double, ndata*N*N*ddim*sigma*sigma)
shared_data = np.ctypeslib.as_array(shared_data_base.get_obj())
shared_data = shared_data.reshape(-1, N, N, ddim*sigma*sigma)
这对sigma=1
,但对于sigma=3
设备的一个硬盘驱动器慢慢填满,直到不再有可用空间,然后该过程失败并出现以下异常:
OSError: [Errno 28] No space left on device
现在我有两个问题:
- 为什么这段代码甚至会向光盘写入任何内容?为什么不全部存储在内存中?
- 如何解决这个问题?我可以让 Python 将其完全存储在 RAM 中而不将其写入硬盘吗?或者我可以更改写入此阵列的 HDD 吗?
编辑:我在网上发现了一些东西,表明数组存储在"共享内存"中。但是/dev/shm
设备有更多的可用空间作为/dev/sda1
,由上面的代码填充。 这是此代码的(相关部分)跟踪日志。
编辑#2:我认为我已经找到了解决这个问题的方法。通过查看源代码,我发现multiprocessing
尝试在目录中创建一个临时文件,该目录通过使用
process.current_process()._config.get('tempdir')
在脚本开头手动设置此值
from multiprocessing import process
process.current_process()._config['tempdir'] = '/data/tmp/'
似乎正在解决这个问题。但我认为这不是解决它的最佳方法。那么:还有其他建议如何处理吗?
这些数据大于 500GB。shared_data_base
我的机器上只有 826.2GBsys.getsizeof()
和 1506.6GBpympler.asizeof.asizeof()
.即使它们只有 500GB,您的计算机也需要一些内存才能运行。这就是数据进入磁盘的原因。
import ctypes
from pympler.asizeof import asizeof
import sys
N = 150
ndata = 10000
sigma = 3
ddim = 3
print(sys.getsizeof(ctypes.c_double(1.0)) * ndata*N*N*ddim*sigma*sigma)
print(asizeof(ctypes.c_double(1.0)) * ndata*N*N*ddim*sigma*sigma)
请注意,在我的机器(Debian 9)上,/tmp 是填充的位置。如果发现必须使用磁盘,请确保磁盘上使用的位置具有足够的可用空间,通常/tmp 不是大分区。