在Python中提取列表中的N维数组的元素

时间:2014-04-16 08:39:49

标签: python arrays list matrix cython

我有以下问题。我在一个类中保存了大量数据。大多数这些数据都是时间相关的,在最复杂的情​​况下,变量是三维数组。

因为列表非常灵活(不需要显式声明),所以我想用它们来封装我的N维数组,因此,使用列表来保存时间依赖信息。

这里是我的列表中元素t = 0,t = 2和t = 3的典型示例,它位于历史类(float64的简单矩阵)中:

history.params[0]
array([[ 1.        ,  2.        ,  1.        ],
       [ 1.        ,  2.        ,  1.        ],
       [ 0.04877093,  0.53176887,  0.26210472],
       [ 2.76110434,  1.3569246 ,  3.118208  ]])

history.params[2]
array([[ 1.00000825,  1.99998362,  1.00012835],
       [ 0.62113657,  0.47057772,  5.23074169],
       [ 0.04877193,  0.53076887,  0.26210472],
       [ 0.02762192,  4.99387138,  2.6654337 ]])
history.params[3]
array([[ 1.00005473,  1.99923187,  1.00008009],
       [ 0.62713657,  0.47157772,  5.23074169],
       [ 0.04677193,  0.53476887,  0.25210472],
       [ 0.02462192,  4.89387138,  2.6654337 ]])

现在,我如何读取/提取矩阵的给定坐标(x,y)的所有元素,用于所有时间索引t?

我试着这样做:

history.params[:][0][0]

我得到了

array([ 1.,  2.,  1.])

实际上无论结肠的位置如何,我总是得到相同的值,它对应于我的矩阵的第一行:

"history.params[0][:][0]" returns "array([ 1.,  2.,  1.])" in the shell

"history.params[0][0][:]" returns "array([ 1.,  2.,  1.])"

为什么Python不能在这里区分矩阵的元素和列表的元素?什么是最好的解决方案?

当然,我可以编写一些循环并创建一个重新组织我的数据的新变量,但这有点浪费精力。我确信它存在一个优雅的解决方案。

PS:我要去Cythonize'我的代码在某些时候,所以如果你有一个优化的Cython解决方案来存储这些变量,我也很高兴听到它。

2 个答案:

答案 0 :(得分:2)

我建议使用numpy.array数组而不是嵌套列表。

import numpy as np

# Create some data which would be equal to your "params"
a = np.array([[[1, 2, 3],
               [4, 5, 6],
               [7, 8, 9]],
              [[11, 12, 13],
               [14, 15, 16],
               [17, 18, 19]]])

print(a[0])
# [[1 2 3]
#  [4 5 6]
#  [7 8 9]]

print(a[:, 0, 0])
# [1, 11]

print(a[:, 0:2, 0])
# [[1, 4] 
#  [11, 14]]

此外,numpy可以与给定here的Cython结合使用。

答案 1 :(得分:0)

  

为什么Python不能在这里区分矩阵的元素和列表的元素?什么是最好的解决方案?

由于history.params[0]是列表列表,因此history.params[0][0]是一个列表,因此history.params[0][0][:]list[:],它是内部列表的副本。同样,history.params[0][:]是列表列表的副本,因此history.params[0][:][0](copy of the list of lists)[0],它再次是内部列表的第一行,但是在2D数组的副本中。

如果要展平列表,即将2D数组存储为一个列表,则尺寸为(n,m)的2D数组的NxM处的每个元素将成为展平数组中的元素(n*M + m)。因此,在您发布的4x3中,元素(0,0)是平面列表的元素0,元素(2,1)是元素2 * 3 + 1 = 7,依此类推。

您可以将其扩展到3D数组:大小为KxNxM的数组,您将索引(k,n,m)为元素(k*N*M + n*N + m);同样对于更高的维度。