Prototyping mit Python-Code vor dem Kompilieren



Answers

Ich habe SWIG oder SIP nicht benutzt, aber ich finde das Schreiben von Python-Wrappern mit boost.python sehr leistungsfähig und relativ einfach zu benutzen.

Ich bin nicht klar, was Ihre Anforderungen für die Übergabe von Typen zwischen C / C ++ und Python sind, aber Sie können dies leicht tun, indem Sie entweder einen C ++ - Typ zu Python oder ein generisches boost :: python :: object- Argument für Ihre C ++ API. Sie können auch Konverter registrieren, um Python-Typen automatisch in C ++ - Typen umzuwandeln und umgekehrt.

Wenn Sie boost.python planen, ist das Tutorial ein guter Einstieg.

Ich habe etwas implementiert, das dem, was du brauchst, ähnlich ist. Ich habe eine C ++ - Funktion, die eine Python-Funktion und ein Bild als Argumente akzeptiert und die Python-Funktion auf jedes Pixel im Bild anwendet.

Image* unary(boost::python::object op, Image& im)
{
    Image* out = new Image(im.width(), im.height(), im.channels());
    for(unsigned int i=0; i<im.size(); i++)
    {
        (*out)[i] == extract<float>(op(im[i]));
    }
    return out;
}

In diesem Fall ist Image ein C ++ - Objekt, das Python (einem Bild mit Fließkomma-Pixeln) ausgesetzt ist, und op ist eine Python-definierte Funktion (oder wirklich jedes Python-Objekt mit einem __call__-Attribut). Sie können diese Funktion dann wie folgt verwenden (vorausgesetzt, unary befindet sich im aufgerufenen Bild, das auch Image und eine Ladefunktion enthält):

import image
im = image.load('somefile.tiff')
double_im = image.unary(lambda x: 2.0*x, im)

Was die Verwendung von Arrays mit Boost betrifft, habe ich das persönlich noch nicht gemacht, aber ich kenne die Funktionalität, um Arrays mit Hilfe von Boost python verfügbar zu machen - das könnte hilfreich sein.

Question

Ich habe darüber nachgedacht, eine Peak-Fit-Bibliothek für eine Weile zu schreiben. Ich kenne Python ziemlich gut und plane alles zu Beginn in Python zu implementieren, aber stelle mir vor, dass ich möglicherweise einige Kernroutinen in einer kompilierten Sprache eventuell neu implementieren muss.

IIRC, eine der ursprünglichen Aufgaben von Python war eine Prototyping-Sprache, aber Python ist ziemlich liberal darin, Funktionen, Funktoren, Objekte an Funktionen und Methoden zu übergeben, während ich vermute, dass dasselbe nicht für Sage C oder Fortran gilt.

Was sollte ich über das Entwerfen von Funktionen / Klassen wissen, die ich in die kompilierte Sprache einbinden möchte? Und wie viele dieser möglichen Probleme werden von Bibliotheken wie cTypes, bgen, SWIG , Boost.Python , Cython oder Python SIP behandelt ?

Für diesen speziellen Anwendungsfall (eine passende Bibliothek) stelle ich mir vor, Benutzern zu erlauben, mathematische Funktionen (Guassian, Lorentz etc.) als Python-Funktionen zu definieren, die dann von der kompilierten Code-Fitting-Bibliothek interpretiert werden können. Das Übergeben und Zurückgeben von Arrays ist ebenfalls wichtig.




Python ist ziemlich liberal darin, Funktionen, Funktoren und Objekte an Funktionen und Methoden zu übergeben, während ich vermute, dass das Gleiche nicht für C oder Fortran gilt.

In C können Sie keine Funktion als Argument an eine Funktion übergeben, aber Sie können einen Funktionszeiger übergeben, der eine ebenso gute Funktion ist.

Ich weiß nicht, wie viel das helfen würde, wenn Sie versuchen, C- und Python-Code zu integrieren, aber ich wollte nur ein Missverständnis aufklären.




f2py (Teil von numpy ) ist eine einfachere Alternative zu SWIG und boost.python zum Einbinden von C / Fortran-Zahlen-Code.




Links