mat 释放_无法在Java中释放Mat对象

博主在尝试使用JNI将C的Mat对象传递给Java时遇到问题。当尝试释放由OpenCV Java API创建的Mat对象时,一切正常,但释放自定义代码创建的Mat对象会导致应用程序崩溃。问题可能与C和Java中函数命名不一致有关,具体涉及如何在JNI中正确处理Mat对象的生命周期。
摘要由CSDN通过智能技术生成

我正在尝试使用JNI将Mat对象从C传递给

Java.我查看了OpenCV

Java dll的源代码,我使用的是OpenCV使用的完全相同的代码.当我想从Java发布一个Mat对象时,它是由OpenCV Java API创建的,它工作正常,但是当我想发布一个使用相同代码创建的Mat对象时,我的应用程序崩溃了.

我正在发布我正在使用的代码.如果有人有想法,我将非常感激.提前致谢.

[编辑]

另外我想补充一点,如果你看看代码块3和4中的函数定义在Java和C中有相同的函数名,readImage0,但是在C和1中的2个函数名称上有一个额外的1个名字,imread_11和imread_1,这两者是如何联系起来的?也许还有一个我不知道的额外层.

[/编辑]

[EDIT2]

在Windows 7上运行VC11,尝试使用OpenCV 2.4.5和2.4.8

[/ EDIT2]

1.这是在OpenCV源中传递Mat对象的C代码:

JNIEXPORT jlong JNICALL Java_org_opencv_highgui_Highgui_imread_11 (JNIEnv*, jclass, jstring);

JNIEXPORT jlong JNICALL Java_org_opencv_highgui_Highgui_imread_11

(JNIEnv* env, jclass , jstring filename)

{

static const char method_name[] = "highgui::imread_11()";

try {

LOGD("%s", method_name);

const char* utf_filename = env->GetStringUTFChars(filename, 0); std::string n_filename( utf_filename ? utf_filename : "" ); env->ReleaseStringUTFChars(filename, utf_filename);

Mat _retval_ = cv::imread( n_filename );

return (jlong) new Mat(_retval_);

} catch(const std::exception &e) {

throwJavaException(env, &e, method_name);

} catch (...) {

throwJavaException(env, 0, method_name);

}

return 0;

}

2.这是OpenCV源代码中的Java代码:

public static Mat imread(String filename)

{

Mat retVal = new Mat(imread_1(filename));

return retVal;

}

private static native long imread_1(String filename);

这是我的代码:

JNIEXPORT jlong JNICALL Java_tr_com_guney_opencvcpp2java_OpenCVCpp2Java_readImage0(JNIEnv *env, jclass, jstring imagePath)

JNIEXPORT jlong JNICALL Java_tr_com_guney_opencvcpp2java_OpenCVCpp2Java_readImage0(JNIEnv *env, jclass, jstring imagePath)

{

static const char method_name[] = "OpenCVCpp2Java::readImage0()";

try {

LOGD("%s", method_name);

const char* utf_filename = env->GetStringUTFChars(imagePath, 0); std::string n_filename( utf_filename ? utf_filename : "" ); env->ReleaseStringUTFChars(imagePath, utf_filename);

cv::Mat _retval_ = cv::imread( n_filename );

return (jlong) new cv::Mat(_retval_);

} catch(const std::exception &e) {

throwJavaException(env, &e, method_name);

} catch (...) {

throwJavaException(env, 0, method_name);

}

return 0;

}

这是我的Java代码:

public static Mat readImage(String imagePath)

{

Mat retVal = new Mat(readImage0(imagePath));

return retVal;

}

private static native long readImage0(String imagePath);

5.这是我运行代码的方式:

Mat image = Highgui.imread("e:/image.png"); //this works fine

Highgui.imwrite("e:/imageJava.png", image); // this is to check if image is read correctly and works fine

image.release(); // this works fine

//system.gc(); // this also works fine

Mat image2 = OpenCVCpp2Java.readImage("e:/image.png"); //this works fine

Highgui.imwrite("e:/imageJava2.png", image2); // this is to check if image is read correctly and works fine

image2.release(); // this throws exception!

//system.gc(); // this causes application to crash!

6.这是Exception中的内容:

Exception in thread "main" java.lang.Exception: Unknown exception in JNI code {Mat::n_1release()}

at org.opencv.core.Mat.n_release(Native Method)

at org.opencv.core.Mat.release(Mat.java:1875)

7.这是崩溃报告中写的内容:

Stack: [0x28880000,0x288d0000], sp=0x288cf620, free space=317k

Native frames: (J=compiled Java code, j=interpreted, Vv=VM code, C=native code)

C [ntdll.dll+0x2e3be] RtlInitUnicodeString+0x196

C [ntdll.dll+0x2e023] RtlFreeHeap+0x7e

C [kernel32.dll+0x114ad] HeapFree+0x14

C [opencv_java245.dll+0x48e877] Java_org_opencv_contrib_Contrib_chamerMatching_11+0x429a47

C [opencv_java245.dll+0x904f3] Java_org_opencv_contrib_Contrib_chamerMatching_11+0x2b6c3

C [opencv_java245.dll+0x6516a] Java_org_opencv_contrib_Contrib_chamerMatching_11+0x33a

j org.opencv.core.Mat.n_delete(J)V+0

j org.opencv.core.Mat.finalize()V+4

v ~StubRoutines::call_stub

V [jvm.dll+0xfb88b]

V [jvm.dll+0x18d551]

V [jvm.dll+0xfb90d]

V [jvm.dll+0x96301]

V [jvm.dll+0x990c9]

C [java.dll+0x2100] Java_java_lang_ref_Finalizer_invokeFinalizeMethod+0x39

j java.lang.ref.Finalizer.runFinalizer()V+45

j java.lang.ref.Finalizer.access$100(Ljava/lang/ref/Finalizer;)V+1

j java.lang.ref.Finalizer$FinalizerThread.run()V+24

v ~StubRoutines::call_stub

V [jvm.dll+0xfb88b]

V [jvm.dll+0x18d551]

V [jvm.dll+0xfba31]

V [jvm.dll+0xfba8b]

V [jvm.dll+0xb5e89]

V [jvm.dll+0x119b74]

V [jvm.dll+0x14217c]

C [msvcr71.dll+0x9565] endthreadex+0xa0

C [kernel32.dll+0x1336a] BaseThreadInitThunk+0x12

C [ntdll.dll+0x39f72] RtlInitializeExceptionChain+0x63

C [ntdll.dll+0x39f45] RtlInitializeExceptionChain+0x36

Java frames: (J=compiled Java code, j=interpreted, Vv=VM code)

j org.opencv.core.Mat.n_delete(J)V+0

j org.opencv.core.Mat.finalize()V+4

v ~StubRoutines::call_stub

j java.lang.ref.Finalizer.invokeFinalizeMethod(Ljava/lang/Object;)V+0

j java.lang.ref.Finalizer.runFinalizer()V+45

j java.lang.ref.Finalizer.access$100(Ljava/lang/ref/Finalizer;)V+1

j java.lang.ref.Finalizer$FinalizerThread.run()V+24

v ~StubRoutines::call_stub

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值