关于cuda和opencv混合编译之_自定义算法加速模板,适用于大部分图像处理了

虽然opencv提供了不错的加速算法,但是我们很多自己的算法,没法很好的使用,所以,我们只能用cuda上的算法,但是这样又回到了cuda上面那一套东西来,这里,我们可以使用技巧一点的方式,就是搭载于gpuMat这个结构,来做处理.

 

//这里只是做个引导,但是大部分的算法,都是按下面这个算法的变种而来,废话不多说,


//注意,这个这个是在 cudaCalculate.h文件中的申明.
__global__ void ColorReproductionKernel(cv::cuda::PtrStepSz<uchar3> img_r, cv::cuda::PtrStepSz<uchar3> dst);


// 在 cudaCalculate.cu的实现.


//这个只是单纯的对像素做了拷贝
__global__ void ColorReproductionKernel(cv::cuda::PtrStepSz<uchar3> img_r,  cv::cuda::PtrStepSz<uchar3> dst)
{
	
	int i = threadIdx.x + blockIdx.x * blockDim.x;
	int j = threadIdx.y + blockIdx.y * blockDim.y;

	if (i == 0 && j == 0)
	{
		printf("Grid size: (%d, %d)\n", gridDim.x, gridDim.y);  //可用printf来debug
	}

	if (j < dst.rows && i < dst.cols)
	{

		unsigned char & r = img_r(j, i).x;
	
		dst(j, i) = make_uchar3(b*10+2, g*4, r*5);
		

	}

//这个是让并行的 显卡小运算单元,在计算完成后,要等待其它单元,就是做了同步.
	__syncthreads();

}


//这是在本地,也就是cpu上做的预处理
__host__ int ColorReproduction(const cv::Mat & img_r cv::Mat & local)
{

    if (img_r.data == nullptr)
	{
		std::cout << "数据读取错误" << std::endl;
		return;
	}

	if (cv::cuda::getCudaEnabledDeviceCount() == 0)
	{
		std::cout << "此opencv 编译的时候,没有启动CUDA 模块" << std::endl;
		return;
	}

    int imgWidth = img_r.cols;
	int imgHeight = img_r.rows;

	cv::cuda::GpuMat gpumat_r(imgHeight, imgWidth, CV_8UC3);
    cv::cuda::GpuMat gpumat_dst(imgHeight, imgWidth, CV_8UC3);
    
    gpumat_r.upload(img_r);

    //每个block30*30 个线程,大家注意这里,这里是要依据显卡寄存器来做最优解,需要依据图像的宽高和显卡的运算能力来 做个最优分配.
	dim3 threadsPerBlock(30, 30);

	//计算竖直需要多少个block 
	uint block_num_vertical = (imgHeight + threadsPerBlock.x - 1) / threadsPerBlock.x;

	//计算水平需要多少个block
	uint block_num_horizontal = (imgWidth + threadsPerBlock.y - 1) / threadsPerBlock.y;

	//// gridDim.x=numBlocks.x, gridDim.y=numBlocks.y
	dim3 numBlocks(block_num_horizontal, block_num_vertical);

    ColorReproductionKernel << < numBlocks, threadsPerBlock >> > (gpumat_r,     
    gpumat_dst);

//这句代码,是做同步等待,如 ColorReproductionKernel  做了等待,这里就不需要了
	//cudaThreadSynchronize();

//下载到本地来处理,
    gpumat_dst.download(local);

}


//这里是在 main.cpp 文件中.
void main()
{

cv::Mat src = cv::imread("gray.bmp");
cv::Mat dst = cv::Mat::zeros(src.rows,src.cols,src.typt());
ColorReproduction(src,dst );

}

这个时间,基本可以忽略不计,时间太快了. 0.0019ms .....

ok,大体上,我们在使用opencv_gpu 处理能遇到的情况,都在这里了,自定义什么的,都可以使用这个方式来处理了.

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章