I'm developing an application that does some image processing to detect road signs from images captured from the webcam. The program runs nicely for 2 to 3 minutes, after which it crashes due to lack of memory. I'm not able to retrieve the space that have already been used.
The codes snippet below shows how I'm trying to free the space
public void clearVariables() {
cvClearMemStorage(mem);
cvClearSeq(contours);
cvClearSeq(ptr);
originalImage.deallocateReferences();
intensityChannel.deallocateReferences();
eliminationImage.deallocateReferences();
contourImg.deallocateReferences();
}
mem is cvMemStorage, contours is a cvSeq and all the other variable are IplImage. Each of them is a global variable and the are used by different methods.
Here are two methods that use different variables
public IplImage findContours(IplImage eliminationImage) {
contourImg=cvCreateImage(originalImage.cvSize(),originalImage.depth(),originalImage.nChannels());
contourImg=originalImage.clone();
cvClearMemStorage(mem);
cvClearSeq(contours);
cvFindContours(eliminationImage, mem, contours, Loader.sizeof(CvContour.class) , CV_RETR_EXTERNAL, CV_CHAIN_APPROX_SIMPLE,cvPoint(0,0));
int areaImage=originalImage.height()*originalImage.width();
do {
ptr=cvApproxPoly(contours, Loader.sizeof(CvContour.class), mem, CV_POLY_APPROX_DP, cvContourPerimeter(contours)*0.02, 0);
CvRect bRect=cvBoundingRect(contours,0);
int x=bRect.x();
int y=bRect.y();
int h=bRect.height();
int w=bRect.width();
int areaRect=bRect.height()*bRect.width();
double ratio=(double)w/h;
if ((areaImage / 1500 > areaRect) || (ratio < 1.3) || (ratio > 0.25)) {
cvRectangle(contourImg, cvPoint(x, y), cvPoint(x+w, y+h), CvScalar.RED, 1, CV_AA, 0);
}
///check size end
if (contours.h_next()==null){break;}
contours=contours.h_next();
}
while(!contours.isNull());
cvClearSeq(ptr);
cvClearMemStorage(mem);
return contourImg;
}
public IplImage elimination(IplImage thresholdImage)
{
eliminationImage=cvCreateImage(originalImageSize,originalImageDepth,1);
long areaImage=originalImage.height()*originalImage.width();
cvClearMemStorage(mem);
cvClearSeq(contours);
cvFindContours(thresholdImage, mem, contours, Loader.sizeof(CvContour.class) , CV_RETR_LIST, CV_CHAIN_APPROX_SIMPLE);
while(!contours.isNull() && contours!=null){
CvRect bRect=cvBoundingRect(contours,0);
int x=bRect.x();
int y=bRect.y();
int h=bRect.height();
int w=bRect.width();
int areaRect=bRect.height()*bRect.width();
double ratio=(double)w/h;
if((areaRect<(areaImage/1500))||(ratio>1.3)||(ratio<0.25))
{
//if too small
}
else
{
CvSeq points = cvApproxPoly( contours, Loader.sizeof( CvContour.class ), mem, CV_POLY_APPROX_DP, cvContourPerimeter( contours ) * 0.02, 0 );
cvDrawContours(eliminationImage, points, CvScalar.WHITE, CvScalar.WHITE, 0, 8, CV_FILLED);
cvClearSeq(points);
}
if(contours.h_next()==null){break;}
contours=contours.h_next();
}
cvClearMemStorage(mem);
cvClearSeq(contours);
return eliminationImage;
}
the variables are created in the constructor of the class
public detectSign() {
mem=CvMemStorage.create();
contours=new CvSeq();
ptr=new CvSeq();
originalImage=new IplImage();
}
I'm using javacv for the image processing.