给出下列代码在OpenCL中的运行结果:#include "stdio.h" #include <xmmintrin.h> // Need this for SSE compiler intrinsics #include <math.h> // Needed for sqrt in CPU-only version #include <time.h> int main(int argc, char* argv[]) { printf("Starting calculation...\n"); const int length = 64000; // We will be calculating Y = SQRT(x) / x, for x = 1->64000 // If you do not properly align your data for SSE instructions, you may take a huge performance hit. float *pResult = (float*) _aligned_malloc(length * sizeof(float), 16); // align to 16-byte for SSE __m128 x; __m128 xDelta = _mm_set1_ps(4.0f); // Set the xDelta to (4,4,4,4) __m128 *pResultSSE = (__m128*) pResult; const int SSELength = length / 4; clock_t clock1=clock(); #define TIME_SSE // Define this if you want to run with SSE #ifdef TIME_SSE // lots of stress loops so we can easily use a stopwatch for (int stress = 0; stress < 1000; stress++) { // Set the initial values of x to (4,3,2,1) x = _mm_set_ps(4.0f, 3.0f, 2.0f, 1.0f); for (int i=0; i < SSELength; i++) { __m128 xSqrt = _mm_sqrt_ps(x); // Note! Division is slow. It's actually faster to take the reciprocal of a number and multiply // Also note that Division is more accurate than taking the reciprocal and multiplying #define USE_DIVISION_METHOD #ifdef USE_FAST_METHOD __m128 xRecip = _mm_rcp_ps(x); pResultSSE[i] = _mm_mul_ps(xRecip, xSqrt); #endif //USE_FAST_METHOD #ifdef USE_DIVISION_METHOD pResultSSE[i] = _mm_div_ps(xSqrt, x); #endif // USE_DIVISION_METHOD // Advance x to the next set of numbers x = _mm_add_ps(x, xDelta); } } clock_t clock2=clock(); printf("SIMDtime:%d ms\n",1000*(clock2-clock1)/CLOCKS_PER_SEC); #endif // TIME_SSE #define TIME_NoSSE #ifdef TIME_NoSSE clock_t clock3=clock(); // lots of stress loops so we can easily use a stopwatch for (int stress = 0; stress < 1000; stress++) { clock_t clock3=clock(); float xFloat = 1.0f; for (int i=0 ; i < length; i++) { // Even though division is slow, there are no intrinsic functions like there are in SSE pResult[i] = sqrt(xFloat) / xFloat; xFloat += 1.0f; } } clock_t clock4=clock(); printf("noSIMDtime:%d ms\n",1000*(clock4-clock3)/CLOCKS_PER_SEC); #endif // TIME_noSSE return 0; }
时间: 2024-03-31 21:32:37 浏览: 96
代码中使用了两种方法计算Y = SQRT(x) / x,分别是SSE指令集和CPU计算。其中,SSE指令集使用了并行计算,CPU计算则是串行计算。
代码中先定义了一个长度为64000的数组pResult,用于存储计算结果。接着,使用了SSE指令集中的_mm_set1_ps函数将xDelta设置为(4,4,4,4),并将pResult转换为__m128类型的指针pResultSSE,以便使用SSE指令集进行并行计算。
代码中使用了两个宏定义,分别用于控制是否使用SSE指令集进行计算。在使用SSE指令集进行计算时,先进行了一千次循环以加大计算量,并在每次循环中使用_mm_set_ps函数将x设置为(4,3,2,1)。接着,使用_mm_sqrt_ps函数计算x中每个元素的平方根,并将结果存放在xSqrt中。根据宏定义的不同,使用_mm_div_ps或_mm_rcp_ps和_mm_mul_ps函数计算Y = SQRT(x) / x,并将结果存放在数组pResult中。
在使用CPU进行计算时,同样进行了一千次循环以加大计算量,并使用sqrt函数计算x中每个元素的平方根,再除以x并将结果存放在数组pResult中。
最后,代码输出了SSE指令集和CPU计算的耗时。
相关问题
我的代码#include <stdio.h> #include <iostream> #include <opencv2/opencv.hpp> //opencl #include <opencv2/core/ocl.hpp> using namespace std; using namespace cv; int main(int argc, char **argv) { ocl::setUseOpenCL(true); UMat img; imread("../lena.jpg").copyTo(img); UMat frameGray; int64 start=0,end=0; start = getTickCount(); cvtColor(img, frameGray, COLOR_BGR2GRAY); GaussianBlur(frameGray,frameGray , Size(3,3), 0,0); end = getTickCount(); printf("time: %f ms\n", 1000.0*(end - start)/getTickFrequency()); return 0; }
这段代码使用了 OpenCV 的 ocl 模块,启用了 OpenCL 加速。在运行之前需要确保你的系统已经安装好了 OpenCL 的驱动程序和运行时环境,并且支持你的硬件设备。如果你不确定是否已经安装好了 OpenCL,可以查看 OpenCL 的官方网站,或者查看你的硬件和操作系统的支持情况。
在代码中,首先调用了 `ocl::setUseOpenCL(true)`,启用了 OpenCL 加速。然后读取了一张图像并将其拷贝到 UMat 对象 `img` 中。接着创建了一个 UMat 对象 `frameGray`,用于存储将彩色图像转换为灰度图像后的结果。
在计算过程中,使用了 cvtColor 函数将彩色图像转换为灰度图像,然后使用 GaussianBlur 函数对灰度图像进行高斯模糊处理。最后计算了转换和处理的时间,并打印出来。
需要注意的是,OpenCL 加速不一定能够提升程序的运行速度,具体效果取决于硬件设备和算法实现。在一些情况下,使用 OpenCL 可能会比 CPU 程序运行更慢。因此在实际应用中需要根据具体情况进行选择。
1. #include <stdio.h> 2. #include <stdlib.h> 3. #include <math.h> 4. #include <CL/opencl.h> 5. #include <time.h> 6. 7. // OpenCL kernel. Each work item takes care of one element of c 8. const char* kernelSource = "\n" \ 9. "#pragma OPENCL EXTENSION cl_khr_fp64 : enable \n" \ 10. "__kernel void vecAdd( __global double *a, \n" \ 11. " __global double *b, \n" \ 12. " __global double *c, \n" \ 13. " const unsigned int n) \n" \ 14. "{ \n" \ 15. " //Get our global thread ID \n" \ 16. " int id = get_global_id(0); \n" \ 17. " \n" \ 18. " //Make sure we do not go out of bounds \n" \ 19. " if (id < n) \n" \ 20. " c[id] = a[id] + b[id]; \n" \ 21. "} \n" \ 22. "\n"; 23.
这段代码是一个使用 OpenCL 的向量加法的内核函数的实现。其中第 8 行到第 22 行是内核函数的实现,使用了 OpenCL 的语法。这个内核函数将两个长度为 n 的 double 类型向量 a 和 b 相加得到向量 c,每个工作项处理一个元素。第 4 行包含了 OpenCL 的头文件,第 5 行包含了 time.h 头文件,这个头文件提供了一些时间相关的函数。
阅读全文