大型Nx3阵列的Numpy.Cov产生MemoryError

时间:2017-03-03 01:32:44

标签: python arrays numpy covariance point-clouds

我有一个大小为Nx3的大型2D数组。该数组包含(X,Y,Z)格式的点云数据。我在Ubuntu中使用Python在虚拟环境中从.ply文件中读取数据。

当我试图找到此数组的协方差时, rowvar 设置为 True (意味着每行被视为变量),我得到 < EM>的MemoryError

我知道这会创建一个非常大的数组,显然对我的8 Gb已分配内存来说太大了。如果不增加内存分配,是否有不同的解决方法?是否有不同的方法来计算协方差矩阵元素,以便内存不会过载?

1 个答案:

答案 0 :(得分:1)

您可以将其切成一个循环并仅保留上三角形。

import numpy as np

N = 23000
a = np.random.random((N, 3))
c = a - a.mean(axis=-1, keepdims=True)
out = np.empty((N*(N+1) // 2,))
def ravel_triu(i, j, n):
    i, j = np.where(i>j, np.broadcast_arrays(j, i), np.broadcast_arrays(i, j))
    return i*n - i*(i+1) // 2 + j
def unravel_triu(k, n):
    i = n - (0.5 + np.sqrt(n*(n+1) - 2*k - 1)).astype(int)
    return i, k - (i*n - i*(i+1) // 2)
ii, jj = np.ogrid[:N, :N]
for j in range(0, N, 500):
    out[ravel_triu(j, j, N):ravel_triu(min(N, j+500), min(N, j+500), N)] \
        = np.einsum(
            'i...k,...jk->ij', c[j:j+500], c[j:]) [ii[j:j+500] <= jj[:, j:]]

显然,您的协方差将被完全欠采样,并且协方差矩阵具有高度排名缺陷...