所以我有下面用C扩展python的示例代码
#include <python.h>
static PyObject* sayhello(PyObject* self, PyObject *args) {
const char* name;
if (!PyArg_ParseTuple(arg, "s", &name))
return NULL;
printf("Hello %s !\n", name);
Py_RETURN_NONE;
}
static PyMethodDef HelloMethods[] =
{
{"say_hello", say_hello, METH_VARARGS, "Greet Somebody."},
{NULL, NULL, 0, NULL}
};
PyMODINIT_FUNC inithello(void) {
(void) Py_InitModule("hello", HelloMethods);
}
Run Code Online (Sandbox Code Playgroud)
而我的问题是为什么下面的包装函数静态
static PyObject* sayhello(PyObject* self, PyObject *args) {
Run Code Online (Sandbox Code Playgroud) 我尝试使用Python C api在C++中调用Python中的函数,测试成功。
但是,如果我打算导入一个已经导入其他模块的模块,那么 Pymodule_findmodule 将返回 Null,即使它在那里并创建了一个编译文件。这是我的代码
Py_Initialize();
PySys_SetPath("C:/Users/Mik/Documents/GitHub/youtube-dl");
PyObject * pythonFile = PyImport_ImportModule("test2");
Run Code Online (Sandbox Code Playgroud)
这是该目录中名为 test2.py 的 python 文件,其中包含一个名为 test_dl.py 的文件和一个名为 TESTDL 的类
from test_dl import TESTDL
def someFunction(someInput):
return 12345
Run Code Online (Sandbox Code Playgroud)
一旦我添加了导入行,我的程序就不再将其识别为模块
编辑:结果 test_dl 的第一行为:
from __future__ import unicode_literals
Run Code Online (Sandbox Code Playgroud)
这就是我收到此 ImportError: No module named future的原因
谢谢!
我正在尝试为 Python3 编写一个简单的 C 扩展,当我尝试将字符串添加到字典时它会出现段错误。这是我的代码:
#include <stdio.h>
#include <Python.h>
int main() {
PyObject* dict_p = PyDict_New();
char *val = "idjewijjd";
PyObject* val_p = PyUnicode_FromString(val);
const char *key = "dhsjdshj";
for (int j=0; j<8; j++) {
printf("%d\n", PyUnicode_READ_CHAR(val_p,j));
}
int r = PyDict_SetItemString(dict_p, key, val_p);
return 0;
}
Run Code Online (Sandbox Code Playgroud)
我像这样编译gcc t.c $(python3-config --includes --libs) 并运行它。我得到以下输出:
$ ./a.out
105
100
106
101
119
105
106
106
Segmentation fault (core dumped)
Run Code Online (Sandbox Code Playgroud)
这是 gdb 回溯:
Program received signal SIGSEGV, Segmentation fault.
0x00007ffff78d9b38 in PyUnicode_InternInPlace …Run Code Online (Sandbox Code Playgroud) 我正在按照Python API 的官方教程在 C++ 中为 Python 创建一个简单的扩展类型。但是我无法成功编译我的代码。因为当我T_INT在我的代码中使用时,我收到一个错误说'T_INT' was not declared in this scope。我忘了什么吗?我在教程中找不到答案。
这是我的 C++ 代码:
#define PY_SSIZE_T_CLEAN
#include <python3.6/Python.h>
#include <stddef.h>
typedef struct {
PyObject_HEAD
int num;
} MyObject;
static PyMemberDef MyMembers[] = {
{ "num", T_INT, offsetof(MyObject, num), 0, NULL },
{ NULL }
};
static PyTypeObject MyType = []{
PyTypeObject ret = {
PyVarObject_HEAD_INIT(NULL, 0)
};
ret.tp_name = "cpp.My";
ret.tp_doc = NULL;
ret.tp_basicsize = sizeof(MyObject);
ret.tp_itemsize = 0;
ret.tp_flags = Py_TPFLAGS_DEFAULT; …Run Code Online (Sandbox Code Playgroud) 我一直在努力理解 C 扩展中对 numpy 数组的访问,但我很难理解文档。
编辑:这是我想移植到 c 的代码(grav 函数)
import numpy as np
def grav(p, M):
G = 6.67408*10**-2 # m³/s²T
l = len(p[0])
a = np.empty(shape=(2, l))
a[:, 0] = 0
for b in range(1, l):
# computing the distance between body #b and all previous
d = p[:, b:b+1] - p[:, :b]
d2 = (d*d).sum(axis=0)
d2[d2==0] = 1
XXX = G * d * d2**(-1.5)
# computing Newton formula :
# acceleration undergone by b from all previous …Run Code Online (Sandbox Code Playgroud) 我是Python / C API的新手,虽然我可以使用一些基本功能,但我仍在为此而苦苦挣扎。
PyObject* sum_elements(PyObject*, PyObject *o)
{
Py_ssize_t n = PyList_Size(o);
long total = 0;
if (n < 0)
{
return PyLong_FromLong(total);
}
PyObject* item;
for (int i = 0; i < n; i++)
{
item = PyList_GetItem(o, i);
if (!PyLong_Check(item)) continue;
total += PyLong_AsLong(item);
}
return PyLong_FromLong(total);
}
Run Code Online (Sandbox Code Playgroud)
基本上,这是文档页面上介绍中的功能。它应该接收一个python列表并返回所有元素的总和。如果我通过一个列表,该函数工作正常,如果我通过其他内容,但是出现错误消息
SystemError: c:\_work\5\s\objects\listobject.c:187: bad argument to internal function
Run Code Online (Sandbox Code Playgroud)
这种情况应该由if (n<0)语句处理,如果传递的对象不是列表,则n为-1。
我通过以下方式绑定功能:
static PyMethodDef example_module_methods[] = {
{ "sum_list", (PyCFunction)sum_elements, METH_O, nullptr},
{ nullptr, nullptr, 0, nullptr } …Run Code Online (Sandbox Code Playgroud) sysv_ipc我希望以便携的方式使用该库。
我安装了它:
pip3 install sysv_ipc
然后从Python:
import sysv_ipc
sysv_ipc.__file__
# Output:
# /home/x/.local/lib/python3.9/site-packages/sysv_ipc.cpython-39-x86_64-linux-gnu.so
Run Code Online (Sandbox Code Playgroud)
如果我将该文件复制到文件夹(pip uninstall库),然后从该文件夹打开 python 并尝试相同的导入,则会失败。
我尝试检查还安装了哪些内容,结果发现:
/home/x/.local/lib/python3.9/site-packages/sysv_ipc-1.1.0.dist-info
/home/x/.local/lib/python3.9/site-packages/sysv_ipc.cpython-39-x86_64-linux-gnu.so
/home/x/.local/lib/python3.9/site-packages/sysv_ipc-1.1.0.dist-info/INSTALLER
/home/x/.local/lib/python3.9/site-packages/sysv_ipc-1.1.0.dist-info/LICENSE
/home/x/.local/lib/python3.9/site-packages/sysv_ipc-1.1.0.dist-info/METADATA
/home/x/.local/lib/python3.9/site-packages/sysv_ipc-1.1.0.dist-info/RECORD
/home/x/.local/lib/python3.9/site-packages/sysv_ipc-1.1.0.dist-info/REQUESTED
/home/x/.local/lib/python3.9/site-packages/sysv_ipc-1.1.0.dist-info/WHEEL
/home/x/.local/lib/python3.9/site-packages/sysv_ipc-1.1.0.dist-info/top_level.txt
Run Code Online (Sandbox Code Playgroud)
我也没有在setup.py中找到线索。
我想弄清楚的是——
sysv_ipcpip 如何/在哪里与要从该特定文件导入的Python 相关?
我为 numpy 库编写了一个 c 扩展,用于计算特定类型的 bincount。由于缺少更好的名称,我们调用它fast_compiled并将方法签名放在numpy/core/src/multiarray/multiarraymodule.c里面array_module_methods:
{"fast_compiled", (PyCFunction)arr_fast_compiled,
METH_VARARGS | METH_KEYWORDS, NULL},
Run Code Online (Sandbox Code Playgroud)
以及numpy/core/src/multiarray/compiled_base.c(和compiled_base.h)中的实际实现:
NPY_NO_EXPORT PyObject *
arr_fast_compiled(PyObject *NPY_UNUSED(self), PyObject *args, PyObject *kwds)
{
PyObject *list_obj = NULL, *strides_obj = Py_None;
PyArrayObject *list_arr = NULL, *ans = NULL, *strides_arr = NULL;
npy_intp len, ans_size, total_size;
npy_intp i, j, k;
double *dans, *weights;
npy_intp* strides;
static char *kwlist[] = {"weights", "strides", NULL};
if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|O",
kwlist, &list_obj, &strides_obj)) {
goto fail; …Run Code Online (Sandbox Code Playgroud) 我正在编写一个python扩展来提供对Solaris kstat数据的访问(与运送perl库Sun :: Solaris :: Kstat的精神相同),我有一个关于有条件地返回列表或单个对象的问题.python用例看起来像:
cpu_stats = cKstats.lookup(module='cpu_stat')
cpu_stat0 = cKstats.lookup('cpu_stat',0,'cpu_stat0')
正如它当前实现的那样,lookup()返回匹配的所有kstat对象的列表.第一种情况会产生一个对象列表(尽可能多的是CPU),第二种情况会完全指定一个kstat,并返回一个包含一个kstat的列表.
我的问题是,当只有一个匹配时,返回单个对象的形式很差,而当有多个匹配时,返回列表?
谢谢你的周到答案!我的python-fu很弱但是因为像你这样的人而变得越来越强大.
我正在尝试调试一个在 32 位 Python 2.7 中运行良好的扩展模块,但在 64 位 Python 3.5 中却不是那么好。
我使用了 Python.org 的 AMD64 Web 安装程序,但在我得到的链接中
__imp_PyModule_Create2 (referenced in libboost_python-vc120-mt-gd-1_57.lib(module.obj))
Run Code Online (Sandbox Code Playgroud)
未解决。这是唯一未解决的符号。
这是故意的吗?我看到一个旧的错误报告,它似乎表明稳定 ABI 免于调试版本。(这就是为什么我在 SO 上发帖而不是提交错误报告)
如果是故意的,是否预计我会先与 python35_d.lib 链接,然后与 python35.lib 链接,还是有另一种方法来解决这个问题?