python — проблемы с SWIG, mingw32, distutils

Я пытался настроить среду Python 2.7 под Windows 7, чтобы я мог скомпилировать расширение C ++ для использования в Python. Поскольку я новичок в этом, я скачал простой пример Вот и использовал файлы дословно. У меня также есть файл numpy.i в пути. Я настроил свой компьютер с mingw (последняя версия) и swig (v. 3.0.10), и моя версия Python — 2.7.9. Я даже использовал эту среду для компиляции небольшой программы на C ++, используя g ++ без проблем.

Но при попытке создать «простое» расширение Python, указанное выше, я всегда получаю следующий вывод, указывающий на ошибку (я включил команду, которую я выполнил в окне Windows cmd.exe, в качестве первой строки ниже):

python setup.py build -c=mingw32
running build
running build_ext
building '_simple' extension
swigging simple.i to simple_wrap.c
C:\swigwin\swigwin-3.0.10\swig.exe -python -o simple_wrap.c simple.i
C:\MinGW\bin\gcc.exe -mdll -O -Wall -IC:\Python27\lib\site-packages\numpy\core\include -I. -IC:\Python27\include -IC:\Python27\PC -c simple.cc -o build\temp.win32-2.7\Release\simple.o
C:\MinGW\bin\gcc.exe -mdll -O -Wall -IC:\Python27\lib\sitepackages\numpy\core\include -I. -IC:\Python27\include -IC:\Python27\PC -c simple_wrap.c -o build\temp.win32-2.7\Release\simple_wrap.o
writing build\temp.win32-2.7\Release\_simple.def
C:\MinGW\bin\g++.exe -shared -s build\temp.win32-2.7\Release\simple.o build\temp.win32-2.7\Release\simple_wrap.o build\temp.win32-2.7\Release\_simple.def -LC:\Python27\libs -LC:\Python27\PCbuild -lpython27 -lmsvcr90 -o build\lib.win32-2.7\_simple.pyd
build\temp.win32-2.7\Release\simple_wrap.o:simple_wrap.c:(.text+0xce5): undefined reference to `create_list'
build\temp.win32-2.7\Release\simple_wrap.o:simple_wrap.c:(.text+0x170d): undefined reference to `dot'
collect2.exe: error: ld returned 1 exit status
error: command 'C:\\MinGW\\bin\\g++.exe' failed with exit status 1

У меня ужасное чувство, что я упускаю что-то очень простое здесь, но мне удалось успешно скомпилировать эти идентичные файлы в отдельной среде Cygwin без проблем (и да, желательно, чтобы я мог сделать это в не-Cygwin среда).

Я не хочу задушить этот вопрос слишком большим количеством кода, но, для справки, вот файлы simple.i а также setup.py что я использую.

simple.i:
%module simple
%{
#define SWIG_FILE_WITH_INIT
#include "simple.h"%}

%include "numpy.i"%init %{
import_array();
%}

%apply (int DIM1, double* INPLACE_ARRAY1) {(int n0, double *a0)};
%apply (int DIM1, double* IN_ARRAY1) {(int n, double *a), (int m, double *b)};
%apply (int DIM1, double* ARGOUT_ARRAY1) {(int size, double *arr)};
%include "simple.h"
setup.py:
from distutils.core import setup, Extension
import numpy
import os

os.environ['CC'] = 'g++';
setup(name='matt_simple_test', version='1.0', ext_modules =[Extension('_simple',['simple.cc', 'simple.i'], include_dirs = [numpy.get_include(),'.'])])

Если нужен другой код, я с удовольствием выложу их, но опять же другие файлы (simple.cc а также simple.h) используются дословно от Вот.

Итак, вопрос: кто-нибудь может мне помочь исправить эту ошибку?

3

Решение

На этом этапе компиляции входной файл компилируется как код C ++, а функциям в symbol.cc будут заданы символы, несовместимые с C (искажение имени).

C: \ MinGW \ bin \ gcc.exe -mdll -O -Wall
-IC: \ Python27 \ lib \ site-packages \ numpy \ core \ include -I. -IC: \ Python27 \ include -IC: \ Python27 \ PC -c simple.cc -o build \ temp.win32-2.7 \ Release \ simple.o

На этом этапе компиляции входной файл компилируется в виде кода C, и ожидается, что символы для функций в symbols.cc будут разными.

C: \ MinGW \ bin \ gcc.exe -mdll -O -Wall
-IC: \ Python27 \ lib \ sitepackages \ numpy \ core \ include -I. -IC: \ Python27 \ include -IC: \ Python27 \ PC -c simple_wrap.c -o build \ temp.win32-2.7 \ Release \ simple_wrap.o

Один из способов решить эту проблему — добавить swig_opts

setup(name='matt_simple_test', version='1.0',
ext_modules=[Extension('_simple', ['simple.cc', 'simple.i'],
swig_opts=["-c++"],
include_dirs = [numpy.get_include(),'.'])])

Другой вариант заключается в использовании extern "C" в simple.cc

extern "C" double dot(int n, double *a, int m, double *b)
...
extern "C" void create_list(int size, double *arr)
...
1

Другие решения

Других решений пока нет …

По вопросам рекламы [email protected]