Интегрировать Python и C ++ - PullRequest
56 голосов
/ 20 июля 2009

Я изучаю C ++, потому что это очень гибкий язык. Но для интернет-вещей, таких как Twitter, Facebook, Delicious и других, Python кажется гораздо лучшим решением.

Возможно ли объединить C ++ и Python в одном проекте?

Ответы [ 11 ]

89 голосов
/ 20 июля 2009

Взаимодействие Python с C / C ++ - непростая задача.

Здесь я копирую / вставляю предыдущий ответ на предыдущий вопрос для различных методов написания расширения Python. Благодаря Boost.Python, SWIG, Pybindgen ...

  • Вы можете написать расширение самостоятельно на C или C ++ с помощью Python C-API .

    Одним словом: не делайте этого, кроме как научиться это делать. Это очень сложно сделать правильно. Вам придется увеличивать и уменьшать ссылки вручную и писать много кода только для того, чтобы представить одну функцию с очень небольшим количеством преимуществ.

  • Swig

    pro: вы можете создавать привязки для многих языков сценариев.

    минусы: мне не нравится, как работает парсер. Я не знаю, добились ли они какого-то прогресса, но два года назад парсер C ++ был довольно ограниченным. Большую часть времени мне приходилось копировать / вставлять заголовки .h, чтобы добавить несколько символов % и дать дополнительные подсказки анализатору swig.

    Мне также приходилось время от времени иметь дело с C-API Python для (не очень) сложных преобразований типов.

    Я больше этим не пользуюсь.

  • Boost.Python

    про: Это очень полная библиотека. Это позволяет вам делать практически все, что возможно с C-API, но на C ++. Мне никогда не приходилось писать код C-API с этой библиотекой. Я также никогда не сталкивался с ошибкой из-за библиотеки. Код для привязок либо работает как брелок, либо отказывается компилироваться.

    Вероятно, это одно из лучших доступных решений, если у вас уже есть библиотека C ++ для привязки. Но если у вас есть только небольшая функция C для перезаписи, я, вероятно, попробую с Cython.

    cons: если у вас нет предварительно скомпилированной библиотеки Boost.Python, вы собираетесь использовать Bjam (что-то вроде замены make). Я действительно ненавижу Bjam и его синтаксис.

    Библиотеки Python, созданные с помощью B.P, имеют тенденцию к ожирению. Для их компиляции также требуется лот времени.

  • Py ++ : это Boost.Python стало проще. Py ++ использует синтаксический анализатор C ++ для чтения вашего кода, а затем автоматически генерирует код Boost.Python. У вас также есть большая поддержка от его автора (нет, это не я ;-)).

    минусы: только проблемы из-за самого Boost.Python.

    Редактировать Этот проект выглядит прекращенным. Хотя, вероятно, все еще работает, может быть, лучше рассмотреть возможность переключения.

  • Pybindgen

    Генерирует код, связанный с C-API. Вы можете описать функции и классы в файле Python или позволить Pybindgen читать ваши заголовки и автоматически генерировать привязки (для этого используется pygccxml, библиотека python, написанная автором Py ++).

    минусов: это молодой проект с меньшей командой, чем Boost.Python. Есть все еще некоторые ограничения: вы не можете выставлять свои собственные исключения C ++, вы не можете использовать множественное наследование для ваших классов C ++.

    В любом случае, стоит попробовать!

  • Pyrex и Cython :

    Здесь вы пишете не настоящий C / C ++, а смесь Python и C. Этот промежуточный код сгенерирует обычный модуль Python.

Редактировать 22 июля 2013: Теперь Py ++ выглядит прекращенным, сейчас я ищу хорошую альтернативу. В настоящее время я экспериментирую с Cython для моей библиотеки C ++. Этот язык представляет собой смесь между Python и C. Внутри функции Cython вы можете использовать сущности Python или C / C ++ (функции, переменные, объекты, ...).

Cython довольно прост в освоении, имеет очень хорошую производительность, и вы даже можете полностью избегать C / C ++, если вам не нужно взаимодействовать с устаревшими библиотеками C ++.

Однако для C ++ это связано с некоторыми проблемами. Он менее «автоматичен», чем Py ++, поэтому, вероятно, лучше для стабильного API C ++ (что в настоящее время относится к моей библиотеке). Самая большая проблема, которую я вижу с Cython, связана с полиморфизмом C ++. С Py ++ / boost: python я смог определить виртуальный метод в C ++, переопределить его в Python и вызвать версию Python в C ++. С Cython это все еще выполнимо, но вам нужно явно использовать C-Python API.

Изменить 2017-10-06:

Существует новый, pybind11 , похожий на Boost.Python, но с некоторыми потенциальными преимуществами. Например, он использует возможности языка C ++ 11, чтобы упростить создание новых привязок. Кроме того, это библиотека только для заголовков, поэтому перед ее использованием не нужно ничего компилировать, и нет библиотеки для ссылок.

Я немного поиграл с ним, и он действительно был довольно простым и приятным в использовании. Единственное, чего я боюсь, так это того, что, как и Boot.Python, это может привести к длительному времени компиляции и большим библиотекам. Я еще не сделал ни одного теста.

9 голосов
/ 20 июля 2009

Да, это возможно, поощряется и документируется . Я сделал это сам и нашел, что это очень легко.

3 голосов
/ 05 октября 2017

Я бы порекомендовал посмотреть, как PyTorch осуществляет их интеграцию.

3 голосов
/ 20 июля 2009

Мы очень успешно используем swig в нашем продукте.

По сути, Swig берет ваш код C ++ и генерирует вокруг него оболочку Python.

3 голосов
/ 20 июля 2009

Попробуйте Pyrex . Облегчает написание расширений C ++ для Python.

3 голосов
/ 20 июля 2009

Справочное руководство по API Python / C - API, используемый программистами на C и C ++, которые хотят писать модули расширения или встраивать Python.

Расширение и встраивание интерпретатора Python

описывает, как писать модули на C или C ++ для расширения интерпретатора Python новыми модулями. Эти модули могут определять новые функции, а также новые типы объектов и их методы. В документе также описывается, как встроить интерпретатор Python в другое приложение для использования в качестве языка расширения. Наконец, в нем показано, как компилировать и связывать модули расширения, чтобы их можно было динамически загружать (во время выполнения) в интерпретатор, если базовая операционная система поддерживает эту функцию.

2 голосов
/ 01 марта 2012

Это зависит от ваших требований к мобильности. Некоторое время я боролся с этим, и в итоге я обернул свой C ++, используя python API напрямую, потому что мне нужно что-то, что работает в системах, где администратор собирал только работающий в основном gcc и установка на python.

Теоретически Boost.Python должен быть очень хорошим вариантом, поскольку Boost доступен (почти) везде. К сожалению, если вы окажетесь в ОС с более старой установкой Python по умолчанию (наше сотрудничество застряло с 2.4), вы столкнетесь с проблемами, если попытаетесь запустить Boost.Python с более новой версией (мы все используют Python 2.6). Поскольку ваш администратор, вероятно, не удосужился установить версию Boost, соответствующую каждой версии Python, вам придется создавать ее самостоятельно.

Так что, если вы не возражаете против необходимости установки Boost в каждой системе, на которой работает ваш код, используйте Boost.Python. Если вам нужен код, который определенно будет работать в любой системе с Python и компилятором C ++, используйте Python API.

2 голосов
/ 20 июля 2009

Я использовал PyCxx http://cxx.sourceforge.net/ в прошлом и обнаружил, что это очень хорошо.

Он очень элегантно оборачивает API Python C и делает его очень простым в использовании. Очень легко написать расширение Python на C ++. Он снабжен наглядными примерами, поэтому его легко начать.

Мне очень понравилось использовать эту библиотеку, и я рекомендую ее.

2 голосов
/ 20 июля 2009

Смотрите это:

Расширение Python с помощью C или C ++

"Довольно просто добавить новые встроенные модули в Python, если вы знаете, как программировать на C. Такие модули расширения могут делать две вещи, которые нельзя сделать непосредственно в Python: они могут реализовывать новые встроенные модули. в типах объектов, и они могут вызывать функции библиотеки C и системные вызовы.

Для поддержки расширений Python API (интерфейс прикладных программ) определяет набор функций, макросов и переменных, которые обеспечивают доступ к большинству аспектов системы Python во время выполнения. Python API включен в исходный файл C, включая заголовок «Python.h». «

http://www.python.org/doc/2.5.2/ext/intro.html

PS Это пишется "интегрировать":)

1 голос
/ 16 августа 2013

Еще один интересный способ сделать это - генерирование кода на python путем запуска самого python для анализа заголовочных файлов c ++. Команда OpenCV успешно применила этот подход , и теперь они сделали то же самое, чтобы создать оболочку Java для библиотеки OpenCV. Я нашел этот созданный чистый Python API без ограничений, вызванных определенной библиотекой.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...