最善の方法は、 Get<PrimitiveType>ArrayElements ルーチンを使用することです。うまくいけば、VM はピニングをサポートします:
jdoubleArray in2 = env->NewDoubleArray(1000);
jboolean isCopy;
jdouble *elems2 = env->GetDoubleArrayElements(in2, &isCopy);
for(int i = 0; i < 1000; i++)
{
elems2[i] = (jdouble)inputArray[i];
}
env->ReleaseDoubleArrayElements(in2, elems2, 0);
elems2 = NULL;
GetDoubleArrayElements() の呼び出しの後である場合、コピーは作成されていませisCopy
ん。JNI_FALSE
編集:質問を読み直した後、Archie のアイデアの実装を検討することをお勧めします。これは、Java メソッドがデータをどのように使用するかによって異なります。Java メソッドが配列全体を使用しない場合、または一度にすべてを使用しない場合は、C++ 配列の Java クラス ラッパーを作成するという Archie のソリューションが、ネイティブ アクセサーを使用して適切なソリューションになる可能性があります。ただし、Java メソッドがすべてのデータを必要とする場合は、GetDoubleArrayElements() が提供する、VM にデータを取得するための最も迅速な方法が必要な場合があります。
C++ 配列のいくつかの要素に変更を加え、Java コピーにも同じ変更を加えたい場合は、SetDoubleArrayRegion()の出番です。
EDIT2:アーチーは次のようなものを指していると思います:
public class NativeDoubleArrayProxy {
// This is the native `inputArray' pointer.
private long p;
private int length;
private NativeDoubleArrayProxy(long p, int length) {
this.p = p;
this.length = length;
}
public int length() {
return length;
}
public native double getDouble(int index);
public native void getDoubles(int startingIndex, double[] out, int outOffset, int length);
}
正確な詳細は、あなたの型によって異なりますinputArray
(生の C スタイルの配列ですか、それともstd::vector<double>
、何か他のものですか?)。しかし、考え方としてはNativeDoubleArrayProxy
、JNI 側でオブジェクトを構築し、それにキャストされたポインタを に渡すことjlong
です。getDouble() および getDoubles() の JNI 実装は、C++ から Java へのコピー コードを実装します。
もちろん、ポインターが有効なままであることを確認するには、細心の注意を払う必要があります。
参照: Java オブジェクト内にネイティブ ポインターを格納する「正しい」方法は何ですか?