質問

Pythonでは、共有ライブラリのエントリポイントを呼び出すために、ctypesよりもSWIGが適しているのはどのような状況ですか? SWIGインターフェースファイルがまだない場合を考えてみましょう。

2つのパフォーマンスメトリックは何ですか?

役に立ちましたか?

解決

SWIGは(ややugい)CまたはC ++コードを生成します。単純な関数(直接変換できるもの)に使用するのは簡単で、より複雑な関数(Pythonで表現するために追加の変換ステップが必要な出力パラメーターを持つ関数など)には比較的簡単に使用できます。インターフェイスファイルの一部としてCのビットを書き込む必要があります。単純な使用法以外の場合は、CPythonと、それがオブジェクトをどのように表すかについて知る必要があります。難しいことではありませんが、覚えておく必要があります。

ctypesを使用すると、C関数、構造体、およびその他のデータに直接アクセスし、任意の共有ライブラリをロードできます。このためにCを記述する必要はありませんが、Cの動作を理解する必要があります。 SWIGの裏側であると主張することができます:それはコードを生成せず、実行時にコンパイラを必要としませんが、単純な使用以外の場合は、Cデータ型、キャスト、メモリ管理とアライメント作業。また、C構造体、共用体、配列を、適切なメモリレイアウトを含む同等のctypesデータ構造に手動または自動で変換する必要があります。

純粋な実行では、SWIGはctypesよりも高速である可能性があります。実際の作業に関する管理は、実行時のPythonではなくコンパイル時にCで行われるためです。ただし、多くの異なるC関数をそれぞれ数回だけインターフェースしない限り、オーバーヘッドが実際に顕著になることはほとんどありません。

開発時には、ctypesの起動コストははるかに低くなります。インターフェイスファイルについて学習する必要はありません。.cファイルを生成してコンパイルする必要はありません。チェックアウトして黙らせる必要はありません。警告。ただジャンプして、最小限の労力で単一のC関数の使用を開始し、それをさらに拡張できます。そして、Pythonインタープリターで直接テストして試してみることができます。大量のコードをラップするのは少し面倒ですが、それをより簡単にする試みもあります(ctypes-configureなど)。

一方、

SWIGは、複数の言語のラッパーを生成するために使用できます(前述のカスタムCコードのように、入力が必要な言語固有の詳細は除きます)。SWIGができる多くのコードをラップする場合少しの助けで処理できるので、コード生成はctypesの同等のものよりもセットアップがはるかに簡単になります。

他のヒント

swigを使用した豊富な経験があります。 SWIGは、それが物を包むための迅速な解決策であると主張しています。しかし、実際には...


短所:

SWIGは、すべての人および20以上の言語向けに一般的になるように開発されています。一般的に、それは欠点につながります:
-構成が必要です(SWIG .iテンプレート)。時には注意が必要です。
-いくつかの特別なケースの処理の欠如(Pythonプロパティをさらに参照)、
-一部の言語のパフォーマンスの欠如。

Pythonの短所:

1)コードスタイルの不一致。 C ++とpythonのコードスタイルは非常に異なっているので(確かに明らかです)、ターゲットコードをよりPythonishにするための大きな可能性は非常に限られています。例として、ゲッターとセッターからプロパティを作成することは非常に重要です。 このq& a

をご覧ください。

2)広範なコミュニティの欠如。 SWIGにはいくつかの優れたドキュメントがあります。しかし、ドキュメントにない何かを見つけた場合、情報はまったくありません。ブログもグーグルも役に立ちません。そのため、そのような場合にはSWIGで生成されたコードを深く掘り下げる必要があります...それはひどいことです、言うことができます...

長所:

  • 単純な場合、それは非常に迅速で簡単で簡単です

  • swigインターフェースファイルを一度作成した場合、このC ++コードを他の20以上の言語にラップできます(!!!)。

  • SWIGに関する大きな懸念の1つはパフォーマンスです。バージョン2.04以降、SWIGには「-builtin」フラグが含まれているため、SWIGは他の自動化されたラッピング方法よりも高速になります。少なくともいくつかのベンチマークはこれを示しています。

    >

SWIGを使用するタイミング

だから、私は自分でスウィッグを使うのが良い2つのケースを結論づけました:

2)C ++コードをラップする必要がある場合複数の言語。または、複数の言語のコードを配布する必要がある場合があります。この場合、SWIGの使用は信頼できます。

1)最終的に使用するために、C ++ライブラリのいくつかの関数を迅速にラップする必要がある場合。


ライブエクスペリエンス

更新
SWIGを使用してライブラリの変換を行ってから1年半が経ちました。

最初に、Pythonバージョンを作成しました。 SWIGでトラブルが発生した瞬間がいくつかありました-それは本当です。しかし、今はライブラリをJavaと.NETに拡張しました。したがって、1つのSWIGで3つの言語があります。そして、多くの時間を節約するという点で SWIGが揺れると言えます。

更新2
このライブラリにSWIGを使用してから2年です。 SWIGはビルドシステムに統合されています。最近、C ++ライブラリのAPIが大幅に変更されました。 SWIGは完璧に機能しました。必要なことは、.iファイルに複数の%renameを追加して、 CppCamelStyleFunctions()をpythonで looks_more_pythonish にすることだけです。最初に、発生する可能性のある問題について心配しましたが、何も問題はありませんでした。それは驚くべきものだった。いくつかの編集とすべてが3つの言語で配布されました。今では、私たちのケースでSWIGを使用するのが良い解決策であると確信しています。

アップデート3
ライブラリにSWIGを使用するのは3年以上です。 大きな変更:python部分は純粋なpythonで完全に書き直されました。その理由は、現在、ライブラリの大半のアプリケーションでPythonが使用されているためです。純粋なpythonバージョンの動作がC ++のラッピングよりも遅い場合でも、ネイティブライブラリと格闘するのではなく、純粋なpythonを使用する方がユーザーにとって便利です。

SWIGは、.NETおよびJavaバージョンで引き続き使用されます。

ここでの主な質問"プロジェクトを最初から開始した場合、PythonでSWIGを使用しますか?"。します! SWIGにより、当社の製品を迅速に人間に配布することができました

CTypesは非常にクールで、SWIGよりもはるかに簡単ですが、貧弱または悪意を持って記述されたpythonコードが実際にpythonプロセスをクラッシュさせる可能性があるという欠点があります。 boost pythonも検討する必要があります。私見では、実際のswigよりも簡単ですが、最終的なPythonインターフェイスをより詳細に制御できます。とにかくC ++を使用している場合は、他の言語もミックスに追加しないでください。

私の経験では、ctypesには大きな欠点があります。何かがうまくいかない場合(そして、どんな複雑なインターフェースでも常にそうなります)、デバッグするのは大変です。

問題は、スタックの大部分がctypes / ffiマジックによって隠されており、特定のポイントに到達した方法と、パラメーター値がその理由である理由を簡単に判断する方法がないことです。

Pyrex も使用できます。高レベルのPythonコードと低レベルのCコードの間の接着剤として機能します。たとえば、 lxml はPyrexで記述されています。

私は逆説的であり、可能であれば、標準Python API 。 CとPythonの両方の観点から非常によく統合されています。PerlAPIの経験がある場合、非常に嬉しい驚きです。

Ctypesも素晴らしいですが、他の人が言ったように、C ++は行いません。

ラップしようとしているライブラリはどれくらいの大きさですか?コードベースはどれくらい速く変化しますか?その他のメンテナンスの問題はありますか?これらはすべて、おそらくPythonバインディングを記述する最適な方法の選択に影響します。

ctypesは優れていますが、C ++クラスを処理しません。また、ctypesは直接的なCバインディングよりも約10%遅いことがわかりましたが、それはあなたが何を呼び出しているかに大きく依存します。

ctypesを使用する場合は、ctypeバインディングの大規模な例があるPygletおよびPyopenglプロジェクトを確認してください。

まだ言及していなかった考慮事項をいくつか追加したかっただけです。 [編集:おっと、マイク・ステダーの答えが見えなかった]

非Cpython実装(PyPy、IronPython、Jythonなど)を使用する場合、ctypesが唯一の方法です。 PyPyはC拡張機能の記述を許可しないため、pyrex / cythonおよびBoost.pythonは除外されます。同じ理由で、ctypesはIronPythonおよび(最終的には、すべてが機能するようになったら)jythonで機能する唯一のメカニズムです。

他の誰かが言ったように、コンパイルは必要ありません。これは、.dllまたは.soの新しいバージョンが出てきたら、それをドロップインして、その新しいバージョンをロードできることを意味します。いずれのインターフェースも変更されていない限り、ドロップイン交換です。

覚えておくべきことは、SWIGはCPython実装のみを対象としているということです。 ctypesはPyPyおよびIronPythonの実装でもサポートされているため、より広範なPythonエコシステムとの互換性のためにctypesを使用してモジュールを作成する価値があります。

私は、SWIGのアプローチが(Pythonだけでなく一般に)少し肥大化しており、SWIGフレンドリーであるという明確な考え方でPythonコードを書くという痛ましいポイントを超えることなく実装するのが難しいことを発見しましたきれいに書かれたPythonコードを書く。私見では、CバインディングをC ++に書き込み(C ++を使用している場合)、Ctypeを使用してCレイヤーに接続するのがはるかに簡単なプロセスです。

インターフェイスするライブラリにライブラリの一部としてCインターフェイスがある場合、ctypesのもう1つの利点は、サードパーティのライブラリにアクセスするために別個のpython-bindingライブラリをコンパイルする必要がないことです。これは、クロスプラットフォームコンパイルの問題を回避するpure-pythonソリューションを作成する際に特に便利です(異種プラットフォームで提供されるサードパーティライブラリの場合)。コンパイルされたコードをクロスプラットフォームに優しい方法でPyPiのようなものにデプロイしたいパッケージに埋め込む必要があるのは苦痛です。 SWIGまたは基礎となる明示的なCコードを使用するPythonパッケージについての最も苛立たしい点の1つは、クロスプラットフォームでの一般的な利用不能です。クロスプラットフォームで利用可能なサードパーティのライブラリを使用しており、それらを中心にPythonソリューションを開発している場合は、このことを考慮してください。

実際の例として、PyGTKを考えてみましょう。これ(と思う)は、SWIGを使用してCコードを生成し、GTK C呼び出しに接続します。私はこれを最も短い時間だけ使用して、セットアップと使用が本当に苦痛であると感じました。セットアップで正しい順序で作業を行わなかった場合、一般に奇妙なエラーが発生しました。それはとても苛立たしい経験であり、ウェブでGTKが提供するインターフェースの定義を見たとき、Python ctypesインターフェースへのそれらのインターフェースのトランスレーターを書くことは簡単な練習であることに気付きました。 PyGGIと呼ばれるプロジェクトが誕生し、ある日、PyGTKをGTK Cオブジェクト指向インターフェイスにきれいにマッチする、より機能的で便利な製品に書き換えることができました。また、Cコードのコンパイルを必要とせず、クロスプラットフォームに対応しています。 (私は実際にはwebkitgtkに接続した後でしたが、これはクロスプラットフォームではありません)。また、GTKをサポートする任意のプラットフォームにPyGGIを簡単に展開できます。

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top