Saltar al contenido

¿Llamar a C/C++ desde Python?

Posterior a de esta larga búsqueda de datos dimos con la respuesta esta cuestión que suelen tener ciertos usuarios. Te ofrecemos la solución y deseamos que te sea de mucha ayuda.

Solución:

El módulo ctypes es parte de la biblioteca estándar y, por lo tanto, es más estable y está más disponible que swig, que siempre tendía a darme problemas.

Con ctypes, debe satisfacer cualquier dependencia de tiempo de compilación en python, y su enlace funcionará en cualquier python que tenga ctypes, no solo contra el que se compiló.

Supongamos que tiene una clase de ejemplo de C++ simple con la que desea hablar en un archivo llamado foo.cpp:

#include 

class Foo
    public:
        void bar()
            std::cout << "Hello" << std::endl;
        
;

Dado que los ctypes solo pueden hablar con funciones C, debe proporcionar aquellos que los declaran como "C" externo

extern "C" 
    Foo* Foo_new() return new Foo(); 
    void Foo_bar(Foo* foo) foo->bar(); 

A continuación, debe compilar esto en una biblioteca compartida.

g++ -c -fPIC foo.cpp -o foo.o
g++ -shared -Wl,-soname,libfoo.so -o libfoo.so  foo.o

Y finalmente tienes que escribir tu contenedor de python (por ejemplo, en fooWrapper.py)

from ctypes import cdll
lib = cdll.LoadLibrary('./libfoo.so')

class Foo(object):
    def __init__(self):
        self.obj = lib.Foo_new()

    def bar(self):
        lib.Foo_bar(self.obj)

Una vez que tengas eso, puedes llamarlo así

f = Foo()
f.bar() #and you will see "Hello" on the screen

Deberías echarle un vistazo a Boost.Python. Aquí está la breve introducción tomada de su sitio web:

La biblioteca Boost Python es un marco para interactuar con Python y C++. Le permite exponer funciones y objetos de clases de C++ de manera rápida y sin problemas a Python, y viceversa, sin usar herramientas especiales, solo su compilador de C++. Está diseñado para empaquetar las interfaces de C++ de manera no intrusiva, por lo que no debería tener que cambiar el código de C++ para poder empaquetarlo, lo que hace que Boost.Python sea ideal para exponer bibliotecas de terceros a Python. El uso de técnicas avanzadas de metaprogramación por parte de la biblioteca simplifica su sintaxis para los usuarios, de modo que el código envolvente adquiere el aspecto de una especie de lenguaje de definición de interfaz (IDL) declarativo.

La forma más rápida de hacer esto es usando SWIG.

Ejemplo del tutorial SWIG:

/* File : example.c */
int fact(int n) 
    if (n <= 1) return 1;
    else return n*fact(n-1);

Archivo de interfaz:

/* example.i */
%module example
%
/* Put header files here or function declarations like below */
extern int fact(int n);
%

extern int fact(int n);

Construyendo un módulo de Python en Unix:

swig -python example.i
gcc -fPIC -c example.c example_wrap.c -I/usr/local/include/python2.7
gcc -shared example.o example_wrap.o -o _example.so

Uso:

>>> import example
>>> example.fact(5)
120

Tenga en cuenta que debe tener python-dev. Además, en algunos sistemas, los archivos de encabezado de Python estarán en /usr/include/python2.7 según la forma en que lo haya instalado.

Del tutorial:

SWIG es un compilador de C++ bastante completo con soporte para casi todas las características del lenguaje. Esto incluye preprocesamiento, punteros, clases, herencia e incluso plantillas de C++. SWIG también se puede usar para empaquetar estructuras y clases en clases de proxy en el idioma de destino, exponiendo la funcionalidad subyacente de una manera muy natural.

Si haces scroll puedes encontrar las reseñas de otros desarrolladores, tú incluso tienes el poder insertar el tuyo si dominas el tema.

¡Haz clic para puntuar esta entrada!
(Votos: 0 Promedio: 0)


Tags : / /

Utiliza Nuestro Buscador

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *