Python:不同类型的多维数组

时间:2022-02-10 21:28:07

Is it possible to create a multi-dimensional array of different types in Python? The way I usually solve it is [([None] * n) for i in xrange(m)], but I don't want to use list. I want something which is really a continuous array of pointers in memory, not a list. (Each list itself is continuous, but when you make a list of lists, the different lists may be spread in different places in RAM.)

是否可以在Python中创建不同类型的多维数组?我通常解决它的方式是[([无] * n)for x in xrange(m)],但我不想使用list。我想要的东西实际上是内存中连续的指针数组,而不是列表。 (每个列表本身都是连续的,但是当您创建列表列表时,不同的列表可能会分布在RAM中的不同位置。)

Also, writing [([None] * n) for i in xrange(m)] is quite a convoluted way of initializing an empty array, in contrast to something like empty_array(m, n). Is there a better alternative?

另外,在xrange(m)中为i编写[([None] * n)]是一种非常复杂的初始化空数组的方法,与empty_array(m,n)相反。还有更好的选择吗?

2 个解决方案

#1


3  

If you're using numpy, by chance, numpy object arrays are "continuous arrays of pointers in memory".

如果你正在使用numpy,那么numpy对象数组就是“内存中连续的指针数组”。

However, they defeat the usual purpose of numpy arrays, and often wind up being a bad answer to the problem at hand...

然而,它们打败了numpy数组的通常目的,并且经常结束对手头问题的错误答案......

(contiguous memory of the same type --> fast calculations on the entire array... Object arrays don't allow this, as they're just arrays of pointers to python objects.).

(相同类型的连续内存 - >整个数组的快速计算......对象数组不允许这样做,因为它们只是指向python对象的指针数组。)。

Nonetheless, np.empty((m,n), dtype=np.object) does what you want.

尽管如此,np.empty((m,n),dtype = np.object)可以满足您的需求。

E.g.

x = np.empty((3,4), dtype=np.object)
print x
x[2,3] = range(5)
x[1,2] = 2
x[1,3] = (item*2 for item in xrange(10))
print x

Which yields:

Initial array:
[[None None None None]
 [None None None None]
 [None None None None]]

Modified array:
[[None None None None]
 [None None 2 <generator object <genexpr> at 0x8700d9c>]
 [None None None [0, 1, 2, 3, 4]]]

Just be aware that it's going to be much slower and much less memory efficient than "normal" numpy arrays! (i.e. Even a None object takes up quite a bit of memory compared to a (numpy, not python) float, and you've got the additional overhead of the pointer stored in the array. A big object array will use tons of memory!)

请注意,与“普通”numpy数组相比,它会更慢,内存效率更低! (即使是一个None对象占用相当于一个(numpy,而不是python)浮点数的相当大的内存,并且你得到了存储在数组中的指针的额外开销。一个大的对象数组将使用大量的内存! )

However, if what you need is effectively a multi-dimensional list, and you're not going to be appending to it or changing its size frequently, they can be damned convenient. They're essentially meant to be equivalent to matlab's cell arrays, and while there's less of a need for that sort of a data structure in python (python has lists), sometimes it's handy!

但是,如果您需要的是有效的多维列表,并且您不会经常添加或更改其大小,那么它们可能会非常方便。它们本质上意味着相当于matlab的单元格数组,虽然python中不需要那种数据结构(python有列表),但有时候它很方便!

#2


2  

In many cases such arrays are not required as there are more elegant solutions to these problems. Explain what you want to do so someone can give some hints.

在许多情况下,不需要这样的阵列,因为对这些问题有更优雅的解决方案。解释你想做什么,这样有人可以提供一些提示。

Anyway, if you really, really need such data structure, use array.array.

无论如何,如果你真的需要这样的数据结构,请使用array.array。

#1


3  

If you're using numpy, by chance, numpy object arrays are "continuous arrays of pointers in memory".

如果你正在使用numpy,那么numpy对象数组就是“内存中连续的指针数组”。

However, they defeat the usual purpose of numpy arrays, and often wind up being a bad answer to the problem at hand...

然而,它们打败了numpy数组的通常目的,并且经常结束对手头问题的错误答案......

(contiguous memory of the same type --> fast calculations on the entire array... Object arrays don't allow this, as they're just arrays of pointers to python objects.).

(相同类型的连续内存 - >整个数组的快速计算......对象数组不允许这样做,因为它们只是指向python对象的指针数组。)。

Nonetheless, np.empty((m,n), dtype=np.object) does what you want.

尽管如此,np.empty((m,n),dtype = np.object)可以满足您的需求。

E.g.

x = np.empty((3,4), dtype=np.object)
print x
x[2,3] = range(5)
x[1,2] = 2
x[1,3] = (item*2 for item in xrange(10))
print x

Which yields:

Initial array:
[[None None None None]
 [None None None None]
 [None None None None]]

Modified array:
[[None None None None]
 [None None 2 <generator object <genexpr> at 0x8700d9c>]
 [None None None [0, 1, 2, 3, 4]]]

Just be aware that it's going to be much slower and much less memory efficient than "normal" numpy arrays! (i.e. Even a None object takes up quite a bit of memory compared to a (numpy, not python) float, and you've got the additional overhead of the pointer stored in the array. A big object array will use tons of memory!)

请注意,与“普通”numpy数组相比,它会更慢,内存效率更低! (即使是一个None对象占用相当于一个(numpy,而不是python)浮点数的相当大的内存,并且你得到了存储在数组中的指针的额外开销。一个大的对象数组将使用大量的内存! )

However, if what you need is effectively a multi-dimensional list, and you're not going to be appending to it or changing its size frequently, they can be damned convenient. They're essentially meant to be equivalent to matlab's cell arrays, and while there's less of a need for that sort of a data structure in python (python has lists), sometimes it's handy!

但是,如果您需要的是有效的多维列表,并且您不会经常添加或更改其大小,那么它们可能会非常方便。它们本质上意味着相当于matlab的单元格数组,虽然python中不需要那种数据结构(python有列表),但有时候它很方便!

#2


2  

In many cases such arrays are not required as there are more elegant solutions to these problems. Explain what you want to do so someone can give some hints.

在许多情况下,不需要这样的阵列,因为对这些问题有更优雅的解决方案。解释你想做什么,这样有人可以提供一些提示。

Anyway, if you really, really need such data structure, use array.array.

无论如何,如果你真的需要这样的数据结构,请使用array.array。