3

Swig を使用して Java インターフェイスを作成しています。基本的に、C++ にはテンプレートがあります (

template<class T> class TSizedArray
{
    int GetLength();
    T* GetElements() const;
    ...
}

class Producer
{
    TSizedArray<long> GetLongs();
    ...
}

このテンプレートは、SWIG 経由で Java にエクスポートする必要がある API のいくつかの関数の戻り値として使用されます。ただし、Java では、この単純なラッパーの代わりにネイティブ Java 配列を使用したいと考えています。

Java:
    long[] result = Producer.GetLongs();

SWIGでこれを達成する方法がわかりません。テンプレートには複数のインスタンスがあり、異なるクラスの複数のメソッドの入力および出力として使用されます。私は使用できました:

%typemap(jstype) TCustomElementList "long[]"

生成された Java インターフェイスを long[] GetLongs() として取得しますが、生成された実装は TCustomElementList 型の新しいオブジェクトを作成します。

アイデアをありがとう。

4

1 に答える 1

4

あなたはタイプマップで正しい方向に進んでいますが、それだけでなくいくつかのものが必要です:

%module test

template<class T> class TSizedArray
{
public:
    int GetLength();
    T* GetElements() const;
};

%typemap(jstype) TSizedArray<long> "long[]"
%typemap(jtype) TSizedArray<long> "long[]"
%typemap(javaout) TSizedArray<long> {
    return $jnicall;
  }

%typemap(out) TSizedArray<long> {
  $result = JCALL1(NewLongArray, jenv, $1->GetLength());
  JCALL4(SetLongArrayRegion, jenv, $result, 0, $1->GetLength(), $1->GetElements());
}

class Producer
{
public:
    TSizedArray<long> GetLongs();
};

(このインターフェイスは SWIG を正常に実行しましたが、それ以上テストされていません)。

Proxy クラスと JNI クラス (jtype および jstype タイプマップ) の両方の戻り値の型を設定する必要があります。また、JNI コードが返すもの (javaout typemap) を通過するようにプロキシに指示する必要があります。次に、C++ 側 (型マップから) で新しい Java 配列を作成するために挿入される、少しの JNI グルー コードを提供する必要があります。

于 2012-07-02T16:30:24.190 に答える