我在使用SWIG使用Eigen(線性代數封裝)封裝一個小型項目時遇到了問題。我得到一個我不明白的python錯誤,在網上找不到太多內容 - 但我懷疑某處存在一些C++內存損壞。我煮下來到一個玩具例子..但遺憾的是它仍然是合理的長:使用Swig封裝Eigen/C++與Python的錯誤
--- testfunc.cxx ----
#include "Eigen/Dense"
Eigen::VectorXd test(Eigen::MatrixXd data){
Eigen::VectorXd temp;
return temp;
}
--- testswig.i ---- -
%module testswig
%{
#define SWIG_FILE_WITH_INIT
#include "Eigen/Core"
#include <Python.h>
#include <numpy/arrayobject.h>
#include "testfunc.cxx"
%}
%init
%{
import_array();
%}
%include "numpy.i"
%typemap(out) Eigen::VectorXd
{
npy_intp dims[1] = {$1.size()};
PyObject* array = PyArray_SimpleNew(1, dims, NPY_DOUBLE);
double* data = ((double *)PyArray_DATA(array));
for (int i = 0; i != dims[0]; ++i){
*data++ = $1.data()[i];
}
$result = array;
}
%typemap(in) Eigen::MatrixXd (Eigen::MatrixXd TEMP)
{
int rows = 0;
int cols = 0;
rows = PyArray_DIM($input,0);
cols = PyArray_DIM($input,1);
PyArrayObject* temp;
PyArg_ParseTuple($input, "O", &temp);
TEMP.resize(rows,cols);
TEMP.fill(0);
double * values = ((double *) PyArray_DATA($input));
for (long int i = 0; i != rows; ++i){
for(long int j = 0; j != cols; ++j){
// std::cout << "data " << data[i] << std::endl;
TEMP(i,j) = values[i*rows+j];
}
}
}
%include "testfunc.cxx"
--- setup.py ----
from distutils.core import setup, Extension
import numpy
numpyinclude = numpy.__file__[:-12] + 'core/include/'
testswig = Extension('_testswig',
sources=['testswig_wrap.cxx'],
include_dirs=['../', numpyinclude])
setup (name = 'testswig',
version = '0.1',
author = "NoName",
description = """ """,
ext_modules = [testswig],
py_modules = ["testswig"])
-----建築------
我在包含所有3個文件和包含Eigen標題的文件夾'Eigen'的文件夾中構建此文件。這些命令是:
swig -c++ -python -I./ testswig.i
python setup.py install
-------錯誤----------
然後我運行包含
import testswig
import numpy as np
print testswig.test(np.array([[2,3],[4,5]]))
一個Python文件,該文件給出錯誤「SystemError:新樣式getargs格式但參數不是元組」。
注意幾件事: 1)相同的命令直接從python解釋器運行良好。 2)如果函數沒有返回一個Eigen :: VectorXd,或者沒有使用一個Eigen:MatrixXd,它可以正常工作。
謝謝你的時間。
您的python安裝版本3或以上?如果是的話,當你打電話給SWIG時你需要-py3。 – Flexo
不,但很高興知道(您的解決方案是完美的)。 – thebigdog