本文介绍了集成C和Python:ValueError:模块函数无法设置METH_CLASS或METH_STATIC的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在第一次尝试集成C和Python 2.7.3.首先,我只是想为Python写一个可以做基本加法的C模块. (之所以称为npfind,是因为一旦我弄清楚了,我想为numpy写一个find方法)

I am making my first venture into integrating C and Python 2.7.3. For starters, I'm just trying to write a C module for Python that can do basic addition. (It is called npfind because once I figure this out, I want to write a find method for numpy)

npfind.h:

#include <math.h>

extern int add(int a, int b);

npfind.c:

#include "npfind.h"

int add(int a, int b)
{
    return a + b;
}

pynpfind.c:

pynpfind.c:

#include "Python.h"
#include "npfind.h"

static char* py_add_doc = "Adds two numbers.";
static PyObject* py_add(PyObject* self, PyObject* args)
{
    int a, b, r;

    if (!PyArg_ParseTuple(args, "ii", &a, &b))
    {
        return NULL;
    }

    r = a + b;

    return Py_BuildValue("i", r);
}

static PyMethodDef* _npfindmethods = {
    {"add", py_add, METH_VARARGS, py_add_doc},
    {NULL, NULL, 0, NULL}
};

void init_npfind(void)
{
    PyObject* mod;
    mod = Py_InitModule("_npfind", _npfindmethods);
}

npfind.py:

npfind.py:

from _npfind import *

#Do stuff with the methods

npfindsetup.py

npfindsetup.py

from distutils.core import setup, Extension

setup(name="npfind", version="1.0", py_modules = ['npfind.py'],
      ext_modules=[Extension("_npfind", ["pynpfind.c", "npfind.c"])])

毕竟,在Windows 7上,我输入

After all that, on Windows 7, I type

python npfindsetup.py build_ext --inplace --compiler=mingw32

这似乎可行.然后,当我尝试找到npfind.py时,出现此错误:

Which seems to work. When I then try to find npfind.py, I get this error:

Traceback (most recent call last):
  File "npfind.py", line 1, in <module>
    from _npfind import *
ValueError: module functions cannot set METH_CLASS or METH_STATIC

我无法弄清它在说什么.什么是METH_CLASS和METH_STATIC,为什么我要设置它们?

I cannot figure out what it is talking about. What are METH_CLASS and METH_STATIC, and why I am I trying to set them?

推荐答案

您正在将_npfindmethods声明为指针,并尝试将其初始化为数组.当我构建从您的代码段复制的代码时,会收到很多警告,例如:

You are declaring the _npfindmethods as a pointer, and trying to initialize it as an array. When I build a code copied from your snippets, I get a lot of warnings like:

a.c:24:5: warning: braces around scalar initializer [enabled by default]
a.c:24:5: warning: (near initialization for '_npfindmethods') [enabled by default]
a.c:24:5: warning: initialization from incompatible pointer type [enabled by default]
a.c:24:5: warning: (near initialization for '_npfindmethods') [enabled by default]
(...)

变量的初始化值不正确,因此Python在其中查找随机数据.

The variable is initialized with an incorrect value, and thus Python finds random data inside.

您应该将_npfindmethods声明为数组:

static PyMethodDef _npfindmethods[] = {
    {"add", py_add, METH_VARARGS, py_add_doc},
    {NULL, NULL, 0, NULL}
};

现在,它将按照您的期望进行初始化.另外,由于现在py_add_doc需要具有恒定的地址,因此您还必须将其设置为数组:

Now it will be initialized as you expect it to. Also, because now py_add_doc needs to have constant address, you have to make it an array as well:

static char py_add_doc[] = "Adds two numbers.";

因此,您最终的pynpfind.c如下所示:

So, your final pynpfind.c would look like:

#include "Python.h"
#include "npfind.h"

static char py_add_doc[] = "Adds two numbers.";
static PyObject* py_add(PyObject* self, PyObject* args)
{
    int a, b, r;

    if (!PyArg_ParseTuple(args, "ii", &a, &b))
    {
        return NULL;
    }

    r = a + b;

    return Py_BuildValue("i", r);
}

static PyMethodDef _npfindmethods[] = {
    {"add", py_add, METH_VARARGS, py_add_doc},
    {NULL, NULL, 0, NULL}
};

void init_npfind(void)
{
    PyObject* mod;
    mod = Py_InitModule("_npfind", _npfindmethods);
}

这篇关于集成C和Python:ValueError:模块函数无法设置METH_CLASS或METH_STATIC的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

10-28 06:20