Перетворити програму Python у код C / C ++? [зачинено]


149

чи можливо перетворити програму Python на C / C ++?

Мені потрібно реалізувати пару алгоритмів, і я не впевнений, чи є розрив у продуктивності достатньо великий, щоб виправдати весь біль, який я зазнав би, коли робив це в C / C ++ (що мені не вдається). Я думав написати один простий алгоритм і порівняти його проти такого перетвореного рішення. Якщо це одне значно швидше, ніж версія Python, то у мене не буде іншого вибору, ніж це робити в C / C ++.


32
Наскільки Python програє на орієнтирах, майте на увазі, що сповільнення 50x або 100x все ще є незначним, якщо обчислення закінчується за кілька секунд у Python, і навіть не відповідає дійсності, коли ви робите багато вводу-виводу або маєте жахливий алгоритм. Замість того, щоб запитувати "наскільки повільніше Python?" вам слід запитати "чи достатньо швидкий Python?" (і це найпопулярніше, якщо чесно) - це теж швидше, ніж порівняльний аналіз або прохання тут.

1
Реалізація алгоритму в python досить швидка і пряма вперед ... ви просто повинні це зробити, а потім перевірити, чи досить швидко він. У більшості випадків ви можете оптимізувати алгоритм для роботи набагато швидше, використовуючи різні структури даних (dict / set замість списків ...) або різні операції. У будь-якому випадку оптимізація повинна відбутися після того, як ви вже реалізували перший проект алгоритму та порівняли його / профілювали його.
Бакуріу

@delnan: у моєму випадку все стосується часу обчислень. Якщо варіанту C потрібно на x години менше, то я би вклав цей час у те, щоб алгоритми працювали довше / знову. Я просто хочу (приблизно) дізнатись, наскільки повільнішим буде Python - якщо це всього лише пару годин, я, звичайно, не використовую мову, з якою мені не зручно (ви можете зруйнувати найкращі рішення проблем із поганими реалізаціями: П).
CrazyFlyingCloseline

@ delnan правий щодо Python, ймовірно, досить швидкий для багатьох речей. Навіть коли це повільніше, легкість розробки, обслуговування та майбутнє поліпшення є важливими факторами, які слід враховувати.
мартіно

"х годин"? Наскільки це велике? Ви орієнтували реалізацію? У вас є вимірювання? Ви профілювали реалізацію? Або ви намагаєтесь передчасно оптимізувати рішення?
S.Lott

Відповіді:


115

Так. Подивіться на Сітона . Це робиться саме так: перетворює Python на C для прискорень.


6
Звичайно, це нічого не заощадить, якщо ви не додасте купу cdefдекларацій і тим самим не введете статичне введення тексту (інакше ви просто жонглируєте непрозорі PyObject *речі). І він ніколи не буде настільки швидким, як звичайний C, тому що зазвичай це взаємодія з Python (100% або більше? Лише для простого числового коду, який не взаємодіє з Python протягом більшої частини часу!). Але крім цього, так, це може отримати вам досить швидке скорочення.

7
@delnan: Насправді це щось економить. Більш чистий код Python буде швидше після компіляції. Але так, за допомогою cdefs та статичного набору тексту ви дійсно починаєте бачити відмінності. І взаємодія з Python ви отримуєте у всіх випадках, коли ви використовуєте C від Python.
Леннарт Регебро

136

Якщо варіанту C потрібно на x годин менше, то я би вклав цей час у те, щоб алгоритми працювали довше / знову

"Інвестувати" тут не є правильним словом.

  1. Створіть робочу реалізацію в Python. Ви закінчите це задовго до того, як закінчите C-версію.

  2. Виміряйте продуктивність за допомогою профілера Python. Виправте будь-які проблеми, які ви знайдете. Змініть структури даних та алгоритми, як це необхідно, щоб дійсно це зробити правильно. Ви закінчите це задовго до того, як закінчите першу версію в C.

  3. Якщо це все ще занадто повільно, переведіть вручну добре розроблений і ретельно сконструйований Python на C.

    Через те, як працює заднім оглядом, виконання другої версії з існуючого Python (з існуючими тестовими одиницями та з наявними даними профілювання) все одно буде швидше, ніж намагатися зробити код C з нуля.

Ця цитата важлива.

Правило Томпсона для виробників телескопів вперше
Швидше зробити чотирьох-дюймове дзеркало, а потім шість-дюймове дзеркало, ніж зробити шість-дюймове дзеркало.


Інститут Білла Маккінана Ванга


15
Незалежно від величезного балу, я не бачу, як це відповідає на питання.
Audrius Meskauskas

29

Shed Skin - це "(обмежений) компілятор Python-to-C ++".


3
+1 однією перевагою Shed Skin є висновок типу : якщо є можливість відгадати змінні типи з потоку програми, уникнути динамічної перевірки типу. Зазвичай це призводить до скорочення коду C ++, що насправді можна читати та компілювати до більш швидких програм.
Kyss Tao

1
Існує також транспілер Python → 11l → C ++ , який також є компілятором Python до C ++, але він підтримує деякі функції Python, які не підтримуються Shed Skin (наприклад, вкладені функції / закриття).
тав

17

Щойно натрапив на цей новий інструмент у новинах хакерів.

На їхній сторінці - "Nuitka є хорошою заміною інтерпретатора Python і збирає кожну конструкцію, яку пропонує CPython 2.6, 2.7, 3.2 та 3.3. Вона переводить Python у програму C ++, яка потім використовує" libpython "для виконання так само, як і CPython робить це дуже сумісним чином ".


Цей проект настільки зріліший, ніж інші подібні варіанти. Смішно, що він створює двійковий файл з .exeрозширенням на OSX, хоча це абсолютно нормальний виконуваний OSX Mach-O. Схоже , це може бути гарною заміною pyinstaller, py2exe, py2appі т.д. --recurse-***Прапори важливо встановити правильно , хоча.
ccpizza

Nuitka чудова, але створений код C / C ++ використовує PyObject, який пов'язує реалізацію коду CPython-C. Він не виробляє ідіоматичний C-код.
Make42

8

Ще один варіант - перетворити на C ++ крім Shed Skin - це Pythran .

Цитувати високоефективний Python від Micha Gorelick та Ian Ozsvald :

Pythran - компілятор Python-to-C ++ для підмножини Python, що включає часткову numpyпідтримку. Він дуже схожий на Numba та Cython - ви коментуєте аргументи функції, а потім переймаєте її з подальшою анотацією та спеціалізацією коду. Він використовує можливості векторизації та можливості паралелізації на основі OpenMP. Він працює лише з використанням Python 2.7.

Одна дуже цікава особливість Pythran полягає в тому, що він намагатиметься автоматично помітити паралелізаційні можливості (наприклад, якщо ви використовуєте a map) і перетворити це в паралельний код, не вимагаючи від вас додаткових зусиль. Ви також можете вказати паралельні розділи, використовуючи pragma omp > директиви; у цьому відношенні він дуже схожий на підтримку Cython OpenMP.

За лаштунками Pythran візьме як звичайний Python, так і nummy код і спробує агресивно компілювати їх у дуже швидкий C ++ - навіть швидше, ніж результати Cython.

Ви повинні зауважити, що цей проект молодий, і у вас можуть виникнути помилки; Ви також повинні зауважити, що команда розробників дуже доброзичлива і прагне виправити помилки за лічені години.


6

Я знаю, що це старіші теми, але я хотів дати корисну інформацію.

Я особисто використовую PyPy, який дуже просто встановити за допомогою pip. Я взаємозамінно використовую інтерпретатор Python / PyPy, вам взагалі не потрібно міняти свій код, і я виявив, що він приблизно в 40 разів швидший, ніж у стандартного інтерпретатора python (або Python 2x або 3x). Я використовую pyCharm Community Edition для управління своїм кодом, і мені це подобається.

Мені подобається писати код в python, оскільки я думаю, що це дозволяє більше зосередитись на задачі, ніж на мові, що є для мене величезним плюсом. І якщо вам це потрібно ще швидше, ви завжди можете компілювати в двійковий файл для Windows, Linux або Mac (не прямо, але можливо за допомогою інших інструментів). Зі свого досвіду я отримую приблизно 3,5-кратну швидкість над PyPy при компілюванні, що означає на 140 разів швидше, ніж python. PyPy доступний для Python 3x і 2x коду, і знову, якщо ви використовуєте IDE, подібний PyCharm, ви можете легко обмінюватися між скажімо PyPy, Cython і Python (хоча потрібно трохи початкового навчання та налаштування).

Деякі люди можуть посперечатися зі мною на цьому, але я вважаю, що PyPy є швидшим за Cython. Але вони обоє чудовий вибір.

Редагувати: Я хотів би зробити ще одну швидку примітку щодо компіляції: коли ви компілюєте, отриманий бінарний файл набагато більший, ніж ваш сценарій python, оскільки він створює в ньому всі залежності і т.д. тепер додаток буде працювати на будь-якій машині (залежно від того, для якої ОС ви склали, якщо не всі. lol) без Python або бібліотек, він також обробляє ваш код і технічно готовий (до певної міри). Деякі компілятори також генерують код C, який я насправді не переглядав і не бачив, чи це корисно чи просто хитрощі. Удачі.

Сподіваюся, що це допомагає.


2
Я знаю, що це старіший коментар, але дякую!
kfrncs

Без проблем, я радий, що це було корисно.
джек-трейдер

Яке програмне забезпечення ви використовуєте для компіляції з інтерпретації PyPy?
Василь Васьківський

Не конкретно PyPy, просто .py сценарії. Nuitka, якщо ви хочете "C / C ++ виконуваного файлу або C / C ++ вихідного коду" та PyInstaller, якщо ви просто хочете виконати файл (простіше). Також є py2exe, але я мав менший успіх з цим, хоча впевнений, що справи покращилися. PyInstaller також є крос-платформою, не тільки для виконуваних файлів Windows (працює з Linux та Mac). Nuitka є унікальною, тому що я думаю, що це єдиний "компілятор", який повертає вам корисний вихідний код, який ви могли б теоретично оптимізувати далі. Є кілька інших, таких як bbFreeze, cx_Freeze та py2app, але я не пробував їх. Удачі!
джек-трейдер

1
Я також виявив, що PyPy працює швидше, ніж Cython. В одному тесті я фактично виявив PyPy такою ж швидкістю, як і версія C ++ програми (сортування вставки).
Nv7

5

Я розумію, що відповідь на зовсім нове рішення відсутня. Якщо в коді використовується Numpy, я б радив спробувати Pythran:

http://pythran.readthedocs.io/

Для функцій, які я намагався, Pythran дає надзвичайно хороші результати. Отримані в результаті функції так само швидко записуються кодом Fortran (або лише трохи повільніше) і трохи швидше, ніж (досить оптимізоване) рішення Cython.

Перевага порівняно з Cython полягає в тому, що вам просто потрібно використовувати Pythran для функції Python, оптимізованої для Numpy, що означає, що вам не потрібно розширювати цикли та додавати типи для всіх змінних у циклі. Pythran потребує свого часу, щоб проаналізувати код, щоб він зрозумів операції numpy.ndarray.

Це також величезна перевага порівняно з Numba або іншими проектами, заснованими на щойно вкладеній компіляції, для яких (наскільки мені відомо), ви повинні розширити петлі, щоб бути дійсно ефективними. І тоді код з циклами стає дуже неефективним, використовуючи лише CPython та Numpy ...

Недолік Pythran: немає занять! Але оскільки тільки функції, які дійсно потребують оптимізації, мають бути скомпільовані, це не дуже дратує.

Ще один момент: Pythran підтримує (і дуже легко) паралелізм OpenMP. Але я не думаю, що mpi4py підтримується ...


4

http://code.google.com/p/py2c/ виглядає як можливість - вони також згадують на своєму сайті: Cython, Shedskin та RPython і підтверджують, що вони перетворюють код Python в чистий C / C ++, що набагато швидше, ніж C / C ++ пронизаний викликами API Python. Примітка. Я не пробував цього, але збираюся ..


1
Здається, що Py2C все ще є незавершеним проектом. Він не оновлювався протягом декількох років, тому може бути неіснуючим.
Андерсон Грін,
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.