为python模块创建.pxd文件

时间:2016-05-28 20:25:53

标签: python cython

使用cython的一种方法,Python to C编译器, 而不是在Cython中重写你的python代码,只需编写一个与你的模块名称相同的.pxd文件来声明变量的类型,如here中所述

有谁知道自动化或半自动化此过程的方法?

2 个答案:

答案 0 :(得分:3)

你有什么具体的自动化程度? Cython可以使用python模块并将其编译为C,但这只能实现适度的速度增加。大多数速度增加来自提供类型声明。这真的不是你可以自动化的东西。你必须以某种方式提供它们以获得最佳的速度提升。

您可以将类型声明放在aggregate(Price ~ Year + Region, df, mean) 文件中。在Python解释器中运行时,类型声明不起作用。但是在编译时,cython可以使用它们来进行某些优化。例如

<强> some_module.py

.py

<强> some_module.pxd

def myfunction(x, y=2):
    a = x-y
return a + x * y

可以写成:

(a)使用装饰器

cpdef int myfunction(int x, int y=*)

或者,(b)使用注释

@cython.locals(x=cython.int, y=cython.int, a=cython.int)
@cython.returns(cython.int)
def myfunction(x, y=2):
    a = x-y
    return a + x * y

答案 1 :(得分:2)

好吧,我还没有找到一种完全自动化的方法,但半自动化 - 真正需要很小的努力来完全自动化 - 是可用的。

在github上的官方Cython存储库中有一个脚本jedityper.py。这个脚本依赖于Jedi(Python的静态分析器),它接收*.py文件并输出带有装饰器注释的*.py_typed.py文件,如@Dunes答案中所述。

使用您链接的文档中提到的代码:

def myfunction(x, y=2):
    a = x-y
    return a + x * y

def _helper(a):
    return a + 1

class A:
    def __init__(self, b=0):
        self.a = 3
        self.b = b

    def foo(self, x):
        print x + _helper(1.0)

并将其传递给jedityper,您将获得以下内容:

import cython
@cython.locals(a='long', y='long')
def myfunction(x, y=2):
    a = x-y
    return a + x * y

@cython.locals(a='double')
def _helper(a):
    return a + 1

class A:
    @cython.locals(b='long', self='object', a='long')
    def __init__(self, b=0):
        self.a = 3
        self.b = b

    @cython.locals(self='object')
    def foo(self, x):
        print x + _helper(1.0)

如你所见,这只是工作的一半。编写一个解析函数defcython.locals行并执行一些简单匹配的小脚本应该不会太难。