如何有效地将2d python列表提供给c++;扩展模块 我在C++中编写了一个Python 3.5模块,我想从Python到C++输入一个2D列表,最好是一个STD::vector。工作代码如下,但我希望可以避免复制数据,而是将2d数组指
如何有效地将2d python列表提供给c++;扩展模块如何有效地将2d python列表提供给c++;扩展模块 我在C++中编写了一个Python 3.5模块,我想从Python到C++输入一个2D列表,最好是一个STD::vector。工作代码如下,但我希望可以避免复制数据,而是将2d数组指,python,c++,module,Python,C++,Module,如何有效地将2d python列表提供给c++;扩展模块 我在C++中编写了一个Python 3.5模块,我想从Python到C++输入一个2D列表,最好是一个STD::vector。工作代码如下,但我希望可以避免复制数据,而是将2d数组指向地址和输入值。有更好的方法吗 PyObject* CheckTerminal(PyObject* self, PyObject* args) { PyObject *input_value; std::vector<std::v
我在C++中编写了一个Python 3.5模块,我想从Python到C++输入一个2D列表,最好是一个STD::vector。工作代码如下,但我希望可以避免复制数据,而是将2d数组指向地址和输入值。有更好的方法吗
PyObject* CheckTerminal(PyObject* self, PyObject* args)
{
PyObject *input_value;
std::vector<std::vector<bool>> cArray;
if (!PyArg_ParseTuple(args, "O", &input_value))
{
std::cout << "\nerror\n";
goto error;
}
int count = (int)PyList_Size(input_value);
PyObject *ptemp,*vals;
for (int i = 0; i < count; i++)
{
cArray.push_back(std::vector<bool>());
ptemp = PyList_GetItem(input_value, i);
int count2 = (int)PyList_Size(ptemp);
for (int j = 0; j < count2; ++j)
{
vals = PyList_GetItem(ptemp, j);
int v = PyLong_AsLong(vals);
if (v == 1)
{
cArray[i].push_back(true);
}
else if (v == 0)
{
cArray[i].push_back(false);
}
}
}
return PyBool_FromLong(g.CheckTerminal(&cArray));
error:
return 0;
}
我通过使用PyObjor而不是转换为C++数组来解决这个问题。pyobject内的数据访问由PyList_GetItem或PyList_GetSlice完成
// Checks if given boardState is terminal.
PyObject* NInARowGame::CheckTerminal(PyObject* input_value)
{
//this is just check, should be the same number of planes.
PyObject *p1 = PyList_GetItem(input_value, 0);
PyObject *p2 = PyList_GetItem(input_value, 1);
Py_INCREF(p1);
Py_INCREF(p2);
int count = (int)PyList_Size(input_value);
auto nK = this->winsK.size();
for (int i = 0; i<nK; ++i)
{//for each winning kernel do the following
//int ksizeY = k[0].size();
if (compareK(p1, &this->winsK[i]))
{
winner = 1;
return Py_True;
}
if (compareK(p2, &this->winsK[i]))
{
winner = 2;
return Py_True;
}
}
PyObject *m = this->GetMoves();
int counter = (int)PyList_Size(m);
if (counter==0)
{
winner = 3;
return Py_True;
}
Py_DECREF(p1);
Py_DECREF(p2);
return Py_False;
}
//检查给定的boardState是否为terminal。
PyObject*NinaRowName::CheckTerminal(PyObject*输入值)
{
//这只是检查,应该是相同数量的飞机。
PyObject*p1=PyList\u GetItem(输入值,0);
PyObject*p2=PyList\u GetItem(输入值,1);
Py_增量(p1);
Py_增量(p2);
int count=(int)PyList_大小(输入值);
auto nK=this->winsK.size();
对于(int i=0;iwinsK[i]))
{
获胜者=1;
返回Py_True;
}
if(比较(p2,&this->winsK[i]))
{
获胜者=2;
返回Py_True;
}
}
PyObject*m=this->GetMoves();
int计数器=(int)PyList_尺寸(m);
如果(计数器==0)
{
获胜者=3;
返回Py_True;
}
Py_DECREF(p1);
Py_DECREF(p2);
返回Py_False;
}
问题在于Python列表是指针数组,而不是值数组,不是吗?为了完整起见,还有一个已定义的脚本可用,非常接近:#define PyList_GET_ITEM(op,i)(((PyListObject*)(op))->ob ITEM[i])
// Checks if given boardState is terminal.
PyObject* NInARowGame::CheckTerminal(PyObject* input_value)
{
//this is just check, should be the same number of planes.
PyObject *p1 = PyList_GetItem(input_value, 0);
PyObject *p2 = PyList_GetItem(input_value, 1);
Py_INCREF(p1);
Py_INCREF(p2);
int count = (int)PyList_Size(input_value);
auto nK = this->winsK.size();
for (int i = 0; i<nK; ++i)
{//for each winning kernel do the following
//int ksizeY = k[0].size();
if (compareK(p1, &this->winsK[i]))
{
winner = 1;
return Py_True;
}
if (compareK(p2, &this->winsK[i]))
{
winner = 2;
return Py_True;
}
}
PyObject *m = this->GetMoves();
int counter = (int)PyList_Size(m);
if (counter==0)
{
winner = 3;
return Py_True;
}
Py_DECREF(p1);
Py_DECREF(p2);
return Py_False;
}