【问题标题】:using iterator in cython在 cython 中使用迭代器
【发布时间】:2018-09-16 07:47:04
【问题描述】:

我正在尝试学习 cython,我修改了找到的示例 here

#pyx file

import numpy as np
cimport numpy as np
import cython

np.import_array()

def test1(a):
    out = np.empty(a.shape, np.double)

    cdef np.flatiter ita = np.PyArray_IterNew(a)
    cdef np.flatiter ito = np.PyArray_IterNew(out)

    cdef double value

    cdef double i
    i = 0.0

    while np.PyArray_ITER_NOTDONE(ita):

        value = (<double*>np.PyArray_ITER_DATA(ita))[0]

        print(ita)  # for debugging
        print(value,i)  # for debugging

        value = value + i

        (<double*>np.PyArray_ITER_DATA(ito))[0] = value

        i += 1.0

        np.PyArray_ITER_NEXT(ita)
        np.PyArray_ITER_NEXT(ito)

    return out

所以我希望该函数将输入数组的每个元素添加i,其中i 的值在迭代器每次传递到下一个元素时增加一。当我使用a=np.arange(10) 运行该函数时,打印语句显示如下内容:

(2.121995791e-314, 0.0)
(<numpy.flatiter object at 0x0000024A2CE27B20>)

(4.2439915824e-314, 1.0)
(<numpy.flatiter object at 0x0000024A2CE27B20>)

(6.365987374e-314, 2.0)
(<numpy.flatiter object at 0x0000024A2CE27B20>)

(8.4879831653e-314, 3.0)
(<numpy.flatiter object at 0x0000024A2CE27B20>)
# rest not shown here

这不是我所期望的,因为迭代器似乎仍然指向数组的相同元素,value 返回的值基本上为零,但不是a 的值(数字 0 -9)。但是迭代器似乎确实在函数结束时停止了,因为函数成功终止并且返回的数组具有与a 相同的形状。

所以我的问题是:

  1. value = (&lt;double*&gt;np.PyArray_ITER_DATA(ita))[0] 这行实际上是什么意思? &lt;double*&gt; 声明指针类型? np.PyArray_ITER_DATA 正是 API 所说的。那么[0]呢?

  2. 我做错了什么以及如何修改代码?如果a=np.arange(2,8),那么test1(a) 应该给array([ 2, 4, 6, 8, 10, 12])

【问题讨论】:

  • 我认为您正在传入具有整数 dtype 的数组,然后尝试将其读取为双精度
  • @DavidW 你是对的。当我将a 明确声明为float64 类型时,它会按预期工作。为什么这很重要?我的第一个问题仍然存在。我仍然不确定那条线实际上做了什么,我想知道为什么print(ita) 给出相同的地址,即使ita 确实在访问数组的不同元素。

标签: python arrays numpy cython


【解决方案1】:

问题在于 arange 默认为您提供 int 数组,然后您将其解释为好像它是 double 数组(被误解为双精度的小整数通常约为 1e-300 ish,所以这通常是一个很好的线索)。理想情况下,您应该确保检查函数中的dtype

回答您的其他问题:

print(ita) 正在打印迭代器对象的地址,而不是它当前正在访问的数据。因此它总是显示相同的地址。

np.PyArray_ITER_DATA(ita) 获取指向当前数据位地址的指针。由于它被设计为任何 numpy 数组的通用接口,我们不知道类型,所以它是void*&lt;double*&gt; 你是在告诉 Cython 这个指针实际上指向 double[0] 查找存储在该指针处的值

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多