用 C 扩展 python:尝试交换列表元素
Extending python with C: trying to swap list elements
我要为 Python 3.7 构建一个 C 模块,它交换两个列表元素。
这是我的代码,其中读取了两个元素和列表的索引:
static PyObject *st_change(PyObject *self, PyObject *args){
PyObject *pList;
PyObject *tmp1;
PyObject *tmp2;
int i,j;
Py_ssize_t n;
if (!PyArg_ParseTuple(args, "O!ll", &PyList_Type, &pList,&i,&j)) {
PyErr_SetString(PyExc_TypeError, "parameters are wrong.");
return NULL;
}
n = PyList_Size(pList);
tmp1 = PyList_GetItem(pList,i);
tmp2 = PyList_GetItem(pList,j);
PyList_SetItem(pList,i,tmp2);
PyList_SetItem(pList,j,tmp1);
Py_INCREF(pList);
return pList;
}
这适用于一维列表,但当我尝试交换列表列表中的元素时,Python 关闭。
例如,当调用
my_module.st_change([1,2,3],0,1)
结果是
[2,1,3]
当我打电话给
my_module.st_change([[1,2,3],[4,5,6],[7,8,9]],0,1)
python shell 休息
我完全不熟悉 C Python API,如果有人能指出正确的方向,我将不胜感激。谢谢
您正在丢失对 tmp1
的引用。 PyList_SetItem
discards a reference to the item already in that position,因此当您执行 PyList_SetItem(pList,i,tmp2);
时,您 tmp1
会被取消并可能被释放。 int
你不用管它,因为通常有很多对小 int 值的引用。
在调用 PyList_SetItem
之前添加 Py_INCREF(tmp1); Py_INCREF(tmp2);
我要为 Python 3.7 构建一个 C 模块,它交换两个列表元素。 这是我的代码,其中读取了两个元素和列表的索引:
static PyObject *st_change(PyObject *self, PyObject *args){
PyObject *pList;
PyObject *tmp1;
PyObject *tmp2;
int i,j;
Py_ssize_t n;
if (!PyArg_ParseTuple(args, "O!ll", &PyList_Type, &pList,&i,&j)) {
PyErr_SetString(PyExc_TypeError, "parameters are wrong.");
return NULL;
}
n = PyList_Size(pList);
tmp1 = PyList_GetItem(pList,i);
tmp2 = PyList_GetItem(pList,j);
PyList_SetItem(pList,i,tmp2);
PyList_SetItem(pList,j,tmp1);
Py_INCREF(pList);
return pList;
}
这适用于一维列表,但当我尝试交换列表列表中的元素时,Python 关闭。 例如,当调用
my_module.st_change([1,2,3],0,1)
结果是
[2,1,3]
当我打电话给
my_module.st_change([[1,2,3],[4,5,6],[7,8,9]],0,1)
python shell 休息
我完全不熟悉 C Python API,如果有人能指出正确的方向,我将不胜感激。谢谢
您正在丢失对 tmp1
的引用。 PyList_SetItem
discards a reference to the item already in that position,因此当您执行 PyList_SetItem(pList,i,tmp2);
时,您 tmp1
会被取消并可能被释放。 int
你不用管它,因为通常有很多对小 int 值的引用。
在调用 PyList_SetItem
之前添加 Py_INCREF(tmp1); Py_INCREF(tmp2);