处理实时数据,绕过 CvloadImage

Posted

技术标签:

【中文标题】处理实时数据,绕过 CvloadImage【英文标题】:Working with real-time data, bypassing CvloadImage 【发布时间】:2012-06-30 06:28:50 【问题描述】:

这是我们使用 Opencv 显示和处理图像的方式:

int _tmain(int argc, _TCHAR* argv[]) 
    IplImage* img = cvLoadImage( "MGC.jpg" );
    cvThreshold( img, img,  200, 255, CV_THRESH_BINARY );
    cvNamedWindow( "Example1", CV_WINDOW_AUTOSIZE );
    cvShowImage("Example1", img);
    cvWaitKey(0);
    cvReleaseImage( &img );
    cvDestroyWindow( "Example1" );
    return 0;

现在您能帮我实现如下所述的目标吗:

int _tmain(int argc, _TCHAR* argv[]) 
    Some code here (using some API other than OpenCv).... // Captures a frame and  
    //streams the data into a buffer Buf
    Buffer B= Buf; // B contain binary image data i.e 16 bit pixel values
    cvThreshold( B, B,  200, 255, CV_THRESH_BINARY );//Notice I am putting B and not an 
                                                     //Image(legal?)
    cvNamedWindow( "Example1", CV_WINDOW_AUTOSIZE );
    cvShowImage("Example1", B); //Notice I am putting B and not an Image(legal?)   
    cvWaitKey(0);
    cvReleaseImage( &B );
    cvDestroyWindow( "Example1" );
    return 0;

注意我在第二个代码sn-p中没有使用任何硬盘读写操作,比如如下:

  IplImage* img = cvLoadImage( "MGC.jpg" );

基本上我正在处理实时场景,因此我绕过了耗时的cvLoadImage。显然没有将数据保存到硬盘中,我的整个数据还在Buffer B中。这节省了我的时间,这对我的应用程序至关重要。

注意:事实上我会在Buffer B上做更多的处理,比如应用cvminmaxloc等。但是所有这些功能都需要从磁盘加载图像,而不是在我的情况下是一个缓冲区。

能否为我指明正确的方向,以实现使用缓冲区而不是存储在硬盘中的图像的目标?我在理解 openCV 功能时犯了一些错误吗?

更新:

以下建议我可以使用imdecode 从缓冲区读取图像。如上所述,实际上我将使用 OpenCv 函数对图像进行处理,例如 CVMinMaxLoc

 cvThreshold( src, src,  200, 255, CV_THRESH_BINARY );   

现在我可以将Buffer 作为第一个参数而不是cvThreshold( ) 中的图像吗?如果不是,那么使用 openCv 函数处理Buffers(包含像素值)的替代方法是什么?如果没有使用缓冲区的直接方法,那么实现此目标的间接方法是什么?解决方法是什么?

简而言之,我不想在进行任何处理之前将数据带到硬盘上。

【问题讨论】:

你不能将你的缓冲区转换为 Opencv Mat 或 IplImage 类型的缓冲区。那么其余的 opencv 函数可以在缓冲区上工作吗? 【参考方案1】:

了解大部分 OpenCV 的 C 接口处理 IplImage,而不是 Buffer 或任何其他自定义数据类型。换句话说,做:

Buffer B = Buf; 
cvThreshold( B, B,  200, 255, CV_THRESH_BINARY );

将发出编译错误,因为cvThreshold() 要求将数据封装在IplImage 中。

我不想冒成为明显船长的风险,但您需要将Buffer 转换为IplImage。那么你是如何做到这一点的,有人可能会问。好吧,IplImage 是一个简单的数据类型,它将这些重要信息保存在一起:

图片的尺寸(宽/高); 图像的位深度频道数; 以及图像的数据(像素);

还有how do you create a IplImage from scratch?拨打cvCreateImageHeader(),然后拨打cvSetData()

注意:对于 depth 参数,您可能希望使用IPL_DEPTH_16U or IPL_DEPTH_16S。如果您的图像是 RGB,则通道数为 3。使用完IplImage 后,不要忘记调用cvReleaseImage() 以释放它的资源。

我相信真正的挑战是:您将如何从Buffer 中提取所有这些信息。祝你好运!

【讨论】:

【参考方案2】:

C++ OpenCV API 中有imdecode 函数可以解码存储在内存缓冲区中的图像。但旧版 C API 中没有类似物。

【讨论】:

感谢您的帖子。但是如何在使用imdecode读取图像后使用OpenCV的一些处理功能,例如CvMinMaxloc,b'çoz CVMinMaxLoc将第一个参数作为图像而不是缓冲区。【参考方案3】:

我认为您不能将缓冲区(如您所说的具有像素值)代替 src ,即在下面从磁盘加载的图像

  cvThreshold( src, src,  200, 255, CV_THRESH_BINARY );   

一种方法可能是在 MAT 中转换缓冲区,然后使用 cvThreshold。

可能有更多经验的人可能会对此发表评论。

【讨论】:

【参考方案4】:

您应该将缓冲区转换为 openCV 类型 Mat

类似的事情已经完成here

【讨论】:

以上是关于处理实时数据,绕过 CvloadImage的主要内容,如果未能解决你的问题,请参考以下文章

爬虫神器!用它可以实时处理和保存 Ajax 数据

实时计算,流数据处理系统简介与简单分析

日均百亿级日志处理:微博基于Flink的实时计算平台建设

我们可以使用 Hadoop MapReduce 进行实时数据处理吗?

基于 MaxCompute 的实时数据处理实践

Storm简介——实时流式计算介绍