将值的2D数组拆分为X和y数据集

时间:2019-05-21 22:04:18

标签: python arrays numpy

我有以下np.ndarray:

>>> arr
array([[1, 2],
       [3, 4]])

我想将其拆分为X和y,其中每个数组分别是坐标和值。到目前为止,我设法使用np.ndenumerate解决了这个问题:

>>> X, y = zip(*np.ndenumerate(arr))
>>> X 
((0, 0), (0, 1), (1, 0), (1, 1))
>>> y
(1, 2, 3, 4)

我想知道是否有一种更惯用和更快的方法来实现它,因为我实际上处理的数组具有数百万个值。

我需要X和y数组将它们稍后传递给sklearn classifier。上面的格式对我来说似乎是最自然的格式,但是也许有更好的方法可以将它们传递给fit函数。

2 个答案:

答案 0 :(得分:1)

arr重塑为y很容易,您可以通过y = arr.flatten()来实现。我建议将生成X视为单独的任务。

让我们假设您的数据集的形状为NxM。在我们的基准测试中,我们将N设置为500,将M设置为1000。

N = 500
M = 1000
arr = np.random.randn(N, M)

然后通过使用np.mgrid并转换索引,您可以得到如下结果:

np.mgrid[:N, :M].transpose(1, 2, 0).reshape(-1, 2)

基准:

%timeit np.mgrid[:N, :M].transpose(1, 2, 0).reshape(-1, 2)
# 3.11 ms ± 35.3 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)

%timeit zip(*np.ndenumerate(arr))
# 235 ms ± 1.57 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)

根据您的情况,您可以打开包装并通过以下方式获得NM

N, M = arr.shape

然后:

X = np.mgrid[:N, :M].transpose(1, 2, 0).reshape(-1, 2)

答案 1 :(得分:0)

numpy.wherenumpy.ravel()一起使用:

import numpy as np

def ndenumerate(np_array):
    return list(zip(*np.where(np_array+1))), np_array.ravel()

arr = np.random.randint(0, 100, (1000,1000))

X_new, y_new = ndenumerate(arr)
X,y = zip(*np.ndenumerate(arr))

输出(验证):

all(i1 == i2 for i1, i2 in zip(X, X_new))
# True
all(y == y_new)
# True

基准测试(快3倍):

%timeit ndenumerate(arr)
# 234 ms ± 20.5 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)

%timeit zip(*np.ndenumerate(arr))
# 877 ms ± 91.1 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)