Reputation: 1963
Here is my code:
int Factor=3,offset=0,k,l,p,q;
IplImage * image = cvCreateImage(cvSize(img->width, img->height),img->depth, img->nChannels);
cvCopy (img, image, 0);
long double mean=0,nTemp=0,c,sum=0,n=0,s=0,d=0;
int i=0,j=0,krow,kcol;
kernel[0][0]=kernel[0][2]=kernel[2][0]=kernel[2][2]=0;
kernel[0][1]=kernel[1][0]=kernel[1][2]=kernel[2][1]=1;
kernel[1][1]=-4;
uchar* temp_ptr=0 ;
int rows=image->height,cols=image->width,row,col;
//calculate the mean of image and deviation
for ( row = 1; row < rows - 2; row++ )
{
for ( col = 1; col < cols - 2; col++ )
{
nTemp = 0.0;
for (p=0, krow = -1 ; p < 3; krow++,p++)
{
for (q=0, kcol = -1; q < 3; kcol++,q++)
{
temp_ptr = &((uchar*)(image->imageData + (image->widthStep*(row+krow))))[(col+kcol)*3];
for(int k=0; k < 3; k++)
Pixel[p][q].val[k]=temp_ptr[k];
}
}
for (i=0 ; i < 3; i++)
{
for (j=0 ; j < 3; j++)
{
c = (Pixel[i][j].val[0]+Pixel[i][j].val[1]+Pixel[i][j].val[2])/Factor ;
nTemp += (double)c * kernel[i][j];
}
}
sum += nTemp;
n++;
}
}
mean = ((double)sum / n);
for ( row = 1; row < rows - 2; row++ )
{
for ( col = 1; col < cols - 2; col++ )
{
nTemp = 0.0;
for (p=0, krow = -1 ; p < 3; krow++,p++)
{
for (q=0, kcol = -1; q < 3; kcol++,q++)
{
temp_ptr = &((uchar*)(image->imageData + (image->widthStep*(row+krow))))[(col+kcol)*3];
for(int k=0; k < 3; k++)
Pixel[p][q].val[k]=temp_ptr[k];
}
}
for (i=0 ; i < 3; i++)
{
for (j=0 ; j < 3; j++)
{
c = (Pixel[i][j].val[0]+Pixel[i][j].val[1]+Pixel[i][j].val[2])/Factor ;
nTemp += (double)c * kernel[i][j];
}
}
s = (mean - nTemp);
d += (s * s);
}
}
d = d / (n - 1);
d = (sqrt(d));
d=d* 2;
// Write to image
for ( row = 1; row < rows - 2; row++ )
{
for ( col = 1; col < cols - 2; col++ )
{
nTemp = 0.0;
for (p=0, krow = -1 ; p < 3; krow++,p++)
{
for (q=0, kcol = -1; q < 3; kcol++,q++)
{
temp_ptr = &((uchar*)(image->imageData + (image->widthStep*(row+krow))))[(col+kcol)*3];
for(int k=0; k < 3; k++)
Pixel[p][q].val[k]=temp_ptr[k];
}
}
for (i=0 ; i < 3; i++)
{
for (j=0 ; j < 3; j++)
{
c = (Pixel[i][j].val[0]+Pixel[i][j].val[1]+Pixel[i][j].val[2])/Factor ;
nTemp += (double)c * kernel[i][j];
}
}
temp_ptr = &((uchar*)(image->imageData + (image->widthStep*row)))[col*3];
if (nTemp > d)
temp_ptr[0]=temp_ptr[1]=temp_ptr[2]=255;
else
temp_ptr[0]=temp_ptr[1]=temp_ptr[2]=0;
}
}
Where am i going wrong? I have implemented Gaussian Filtering in a similar manner, is there anything wrong in my algorithm?
Upvotes: 1
Views: 397
Reputation: 50328
I noticed is that your code is needlessly complex and inefficient. You don't need to convolve the image before calculating its mean — the convolution just multiplies the mean by the sum of the kernel entries.
Also, since your convolution kernel sums to zero, the mean you get after convolving with it will also (almost) be zero. The only non-zero contributions will come from the edges of the image. I rather doubt that's actually what you want to calculate (and if it is, you could save a lot of time by summing only over the edges in the first place).
Third, as pointed out in another answer (I missed this one myself), you're not averaging over all the color channels, you're averaging over the red channel three times. (Besides, you should probably use a weighted average anyway, after applying gamma correction.)
And finally, as anatolyg said, you're overwriting the image data before you're done reading it. There are several ways to fix that, but the easiest is to write your output to a separate buffer.
Upvotes: 1
Reputation: 28239
It seems that your code (labeled "Write to image") overwrites the input image during the calculations. This is not good. Create a copy of the image, calculate its pixels, then delete the original image.
Upvotes: 1