【发布时间】:2016-02-04 04:36:39
【问题描述】:
我试图切换到新的 OpenCV 3.0,因为它隐式调用 OpenCL 以更快地对矩阵进行运算。我遵循了Sony 提供的一个很好的教程,并且能够集成所需的 OpenCV 文件以使其编译。 我只是在阅读图像检测边缘。在 CPU 和 GPU 端执行相同的操作。但我认为我遗漏了一些重要的东西,因为在这两种情况下处理所需的时间是相同的。代码 sn-ps 如下:
clock_t startTimer1, stopTimer1;
cv::ocl::setUseOpenCL(true);
String path = "/storage/emulated/0/DCIM/100ANDRO/";
String filename = "DSC_0581.JPG";
String filename_result = "DSC_0581_processed.JPG";
ocl::setUseOpenCL(true);
Mat gpuFrame;
UMat gpuBW;
UMat gpuBlur;
UMat gpuEdges;
gpuFrame = imread(path+filename, IMREAD_COLOR);
gpuBW = gpuFrame.getUMat(cv::ACCESS_READ);
startTimer1=clock();
cvtColor(gpuBW, gpuBW, COLOR_BGR2GRAY);
GaussianBlur(gpuBW, gpuBlur, Size(1,1), 1.5, 1.5);
Canny(gpuBlur, gpuEdges, 0, 30, 3);
cv::ocl::finish();
stopTimer1 = clock();
imwrite(path+filename_result, gpuEdges);
double elapse = 1000.0* (double)(stopTimer1 - startTimer1)/(double)CLOCKS_PER_SEC;
info[2] = (int)elapse;
LOGI("OpenCL code on the GPU took %g ms\n\n", 1000.0* (double)(stopTimer1 - startTimer1)/(double)CLOCKS_PER_SEC) ;
以及“纯”本机代码:
ocl::setUseOpenCL(false);
Mat cpuFrame;
String path = "/storage/emulated/0/DCIM/100ANDRO/";
String filename = "DSC_0581.JPG";
String filename_result = "DSC_0581_cpu_processed.JPG";
Mat cpuBW;
Mat cpuBlur;
Mat cpuEdges;
cpuFrame = imread(path+filename);
startTimer=clock();
cvtColor(cpuFrame, cpuBW, COLOR_BGR2GRAY);
GaussianBlur(cpuBW, cpuBlur, Size(1, 1), 1.5, 1.5);
Canny(cpuBlur, cpuEdges, 0, 30, 3);
stopTimer = clock();
imwrite(path+filename_result, cpuEdges);
double elapse = 1000.0* (double)(stopTimer - startTimer)/(double)CLOCKS_PER_SEC;
info[2] = (int)elapse;
LOGI("C++ code on the CPU took %g ms\n\n", 1000.0* (double)(stopTimer - startTimer)/(double)CLOCKS_PER_SEC) ;
在 OpenCV/OpenCL/Android 教程here 中已经提到,需要使用选项编译它
-DWITH_OPENCL=YES
有必要吗?该应用程序编译并运行没有任何错误,但我认为它不能在 GPU 上运行。非常感谢任何帮助!非常感谢!
更新
这是 Android.mk
LOCAL_PATH := $(call my-dir)
LOCAL_PATH_EXT := $(call my-dir)/../extra_libs/
include $(CLEAR_VARS)
#opencv
OPENCVROOT:= C:/Android/opencva3
OPENCV_CAMERA_MODULES:=on
OPENCV_INSTALL_MODULES:=on
OPENCV_LIB_TYPE:=SHARED
-DWITH_OPENCL=YES
include ${OPENCVROOT}/sdk/native/jni/OpenCV.mk
LOCAL_ARM_MODE := arm
LOCAL_MODULE := openclexample1
LOCAL_CFLAGS += -DANDROID_CL -DWITH_OPENCL
LOCAL_CFLAGS += -O3 -ffast-math
LOCAL_C_INCLUDES := $(LOCAL_PATH)/../include
LOCAL_SRC_FILES := sonyOpenCLexample1.cpp openCLNR.cpp refNR.cpp #ocdft.cpp
LOCAL_LDLIBS += -ldl -llog -ljnigraphics
LOCAL_LDLIBS += -lGLESv2 -lEGL
LOCAL_LDLIBS += $(LOCAL_PATH_EXT)libOpenCL.so
include $(BUILD_SHARED_LIBRARY)
【问题讨论】:
-
1.日志中表明正在使用 T-API 库的任何内容。 2. 你测试的是什么设备/操作系统版本。
-
该设备是具有可用 opencllib.so 的 Sony Xperia Z1。我能够运行 Sony 的示例应用程序,它运行良好且快速。 logcat 只提供大量 libEGL 输出。与 T-API 无关。最后三行是:
11-03 22:52:53.415 21768-21794/com.sony.openclexample1 D/libEGL: glEndTilingQCOM(0x00000001); 11-03 22:52:53.418 21768-21794/com.sony.openclexample1 D/libEGL: glGetError(); 11-03 22:52:57.760 21768-21768/com.sony.openclexample1 I/JNIpart: OpenCL code on the GPU took 3034.24 ms -
那么您是否按照链接中有关
-DWITH_OPENCL=YES和System.loadLibrary("opencv_java3")的说明进行操作? -
其实不是。我对“建筑”的东西不太熟悉。我刚刚从他们那里下载了 OpenCV 3.0 Android 并将其放入 Gradle 模块中。你能提供一个显示步骤的好网站吗?我已经更新了上面的 Android.mk,它应该可以在没有 OpenCV 管理器应用的情况下工作,对吧?
-
啊,那么您使用的是常规的 OpenCV,甚至没有设置带有 OpenCL 的东西。无需更改应用程序中的代码以使用不同的库,您将使用 Manager 应用程序。 OpenCL 具有特定于设备/平台的特性(即 NVidia OpenCL 驱动程序将不同于三星或高通),并且在常规 Android 中不受支持。抱歉,步骤 - 最好是了解 Android NDK,因为教程中的代码是 C/C++
标签: android opencv android-studio opencl opencv3.0