視頻前景提取 (II)【IplImage版本】
以下代碼可以求出視頻的前景,用的方法就是拿第一幀做差分。。。
但是以下代碼有個致命的問題,那就是在視頻幀處理的過程中,不斷的create卻不釋放內存,導致了內存溢出。。
#include "cv.h" #include "highgui.h" #include <stdio.h> #include <stdlib.h> #include <string.h> #include <assert.h> #include <math.h> #include <float.h> #include <limits.h> #include <time.h> #include <ctype.h> #ifdef _EiC #define WIN32 #endif static CvMemStorage* storage = 0; int main() { CvCapture* capture = 0; IplImage *frame, *frame_copy = 0,*img1=NULL; char* input_name; input_name = "002.avi"; storage = cvCreateMemStorage(0); if( !input_name || (isdigit(input_name[0]) && input_name[1] == '\0') ) //直接從攝像頭讀入 capture = cvCaptureFromCAM( !input_name ? 0 : input_name[0] - '0' ); else //從AVI視頻讀入 capture = cvCaptureFromAVI( input_name ); cvNamedWindow( "result", 1 ); int flag=0; if( capture ) { //如果捕捉到幀了 //對每一幀做處理 for(;;) { if( !cvGrabFrame( capture )) break; frame = cvRetrieveFrame( capture ); if( !frame ) break; if(flag==0) { //捕捉第一幀 frame_copy = cvCreateImage( cvSize(frame->width,frame->height), IPL_DEPTH_8U, frame->nChannels ); cvCopy(frame,frame_copy,0); flag=1; } img1 = cvCreateImage( cvSize(frame->width,frame->height), IPL_DEPTH_8U, frame->nChannels ); cvAbsDiff(frame,frame_copy,img1); cvShowImage( "src", frame ); cvShowImage( "result", img1 ); //10ms中按任意鍵進入此if塊 if( cvWaitKey( 10 ) >= 0 ) break; } cvReleaseImage( &frame_copy ); cvReleaseImage( &img1 ); cvReleaseCapture( &capture ); } cvDestroyWindow("src"); cvDestroyWindow("result"); return 0; }
為了解決這個問題,可以在開始的時候設置標誌位,隻在第一次的時候create圖片:
#include "cv.h" #include "highgui.h" #include <stdio.h> #include <stdlib.h> #include <string.h> #include <assert.h> #include <math.h> #include <float.h> #include <limits.h> #include <time.h> #include <ctype.h> #ifdef _EiC #define WIN32 #endif int main() { CvCapture* capture = 0; IplImage *frame, *frame_copy = 0,*img1=NULL; char* input_name; input_name = "001.avi"; if( !input_name || (isdigit(input_name[0]) && input_name[1] == '\0') ) //直接從攝像頭讀入 capture = cvCaptureFromCAM( !input_name ? 0 : input_name[0] - '0' ); else //從AVI視頻讀入 capture = cvCaptureFromAVI( input_name ); cvNamedWindow( "result", 1 ); int flag=0; if( capture ) { //如果捕捉到幀了 //對每一幀做處理 for(;;) { if( !cvGrabFrame( capture )) break; frame = cvRetrieveFrame( capture ); if( !frame ) break; if(flag==0) { //捕捉第一幀 if( !frame_copy ) frame_copy = cvCreateImage( cvSize(frame->width,frame->height), IPL_DEPTH_8U, frame->nChannels ); if( frame->origin == IPL_ORIGIN_TL ) cvCopy( frame, frame_copy, 0 ); else cvFlip( frame, frame_copy, 0 ); flag=1; } //為NULL就create一次,不然內存會溢出 if( !img1 ) img1 = cvCreateImage( cvSize(frame->width,frame->height), IPL_DEPTH_8U, frame->nChannels ); cvAbsDiff(frame,frame_copy,img1); cvShowImage( "src", frame ); cvShowImage( "result", img1 ); //10ms中按任意鍵進入此if塊 if( cvWaitKey( 10 ) >= 0 ) break; } cvReleaseImage( &frame_copy ); cvReleaseCapture( &capture ); //不用釋放,因為開始的時候沒有顯式分配內存 //cvReleaseImage( &frame ); //cvReleaseImage( &img1 ); } cvDestroyWindow("src"); cvDestroyWindow("result"); return 0; }
最後更新:2017-04-03 05:39:31