是否可以创建一个包含复杂整数的numpy.ndarray? [英] Is it possible to create a numpy.ndarray that holds complex integers?
问题描述
我想创建在其中包含复杂整数值的numpy.ndarray
对象. NumPy确实具有内置的复杂支持,但仅适用于浮点格式(float
和double
);例如,我可以用dtype='cfloat'
创建一个ndarray
,但是没有类似的dtype='cint16'
.我希望能够创建包含使用8位或16位整数表示的复杂值的数组.
I would like to create numpy.ndarray
objects that hold complex integer values in them. NumPy does have complex support built-in, but for floating-point formats (float
and double
) only; I can create an ndarray
with dtype='cfloat'
, for example, but there is no analogous dtype='cint16'
. I would like to be able to create arrays that hold complex values represented using either 8- or 16-bit integers.
我发现此邮件列表帖子来自2007年有人询问这种支持.他们建议的唯一解决方法是定义一个包含整数对的新dtype
.这似乎将每个数组元素表示为2个值的元组,但是尚不清楚要使结果数据类型与算术函数无缝工作还需要做哪些其他工作.
I found this mailing list post from 2007 where someone inquired about such support. The only workaround they recommended involved defining a new dtype
that holds pairs of integers. This seems to represent each array element as a tuple of 2 values, but it's not clear what other work would need to be done in order to make the resulting datatype work seamlessly with arithmetic functions.
我还考虑了另一种基于文档类型描述符结构似乎表明类型的kind
字段仅支持有符号/无符号整数,浮点数和复杂的浮点数字类型.尚不清楚我是否能够尝试定义复杂的整数类型.
I also considered another approach based on registration of user-defined types with NumPy. I don't have a problem with going to the C API to set this up if it will work well. However, the documentation for the type descriptor strucure seems to suggest that the type's kind
field only supports signed/unsigned integer, floating-point, and complex floating-point numeric types. It's not clear that I would be able to get anywhere trying to define a complex integer type.
对可行的方法有何建议?
Any recommendations on an approach that may work?
编辑:还有一件事;我选择的任何方案都必须能够包装现有的复杂整数缓冲区而无需执行复制.也就是说,我希望能够使用PyArray_SimpleNewFromData()
将缓冲区公开给Python,而不必先创建缓冲区的副本.缓冲区已经是交错的实/虚格式,并且可以是int8_t
或int16_t
的数组.
One more thing; whatever scheme I select must be amenable to wrapping of existing complex integer buffers without performing a copy. That is, I would like to be able to use PyArray_SimpleNewFromData()
to expose the buffer to Python without having to make a copy of the buffer first. The buffer would be in interleaved real/imaginary format already, and would either be an array of int8_t
or int16_t
.
推荐答案
我还处理许多复杂的整数数据,通常是基带数据. 我用
I also deal with lots of complex integer data, generally basebanded data. I use
dtype = np.dtype([('re', np.int16), ('im', np.int16)])
这并不完美,但是可以充分描述数据.我将其用于加载到内存中,而不会增加数据大小.它还具有能够通过HDF5透明地加载和存储的优点.
It's not perfect, but it adequately describes the data. I use it for loading into memory without doubling the size of the data. It also has the advantage of being able to load and store transparently with HDF5.
DATATYPE H5T_COMPOUND {
H5T_STD_I16LE "re";
H5T_STD_I16LE "im";
}
使用起来很简单,只是有所不同.
Using it is straightforward, just different.
x = np.zeros((3,3),dtype)
x[0,0]['re'] = 1
x[0,0]['im'] = 2
x
>> array([[(1, 2), (0, 0), (0, 0)],
>> [(0, 0), (0, 0), (0, 0)],
>> [(0, 0), (0, 0), (0, 0)]],
>> dtype=[('re', '<i2'), ('im', '<i2')])
要对此进行数学运算,我将转换为本机复杂的float类型.显而易见的方法行不通,但也没有那么困难.
To do math with it, I convert to a native complex float type. The obvious approach doesn't work, but it's also not that hard.
y = x.astype(np.complex64) # doesn't work, only gets the real part
y = x['re'] + 1.j*x['im'] # works, but slow and big
y = x.view(np.int16).astype(np.float32).view(np.complex64)
y
>> array([[ 1.+2.j, 0.+0.j, 0.+0.j],
>> [ 0.+0.j, 0.+0.j, 0.+0.j],
>> [ 0.+0.j, 0.+0.j, 0.+0.j]], dtype=complex64)
这最后一种转换方法的灵感来自> https://stackoverflow.com/a/5658446/1784179
This last conversion approach inspired by https://stackoverflow.com/a/5658446/1784179
这篇关于是否可以创建一个包含复杂整数的numpy.ndarray?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!