Hallo together,
working on my project, I have an new problem. I want to speed up my integration of brightness of a bitmap. Therefor I got two different types of calculation algorithms. The first one is the "classical" slow algorithm by iterating through the pixels and get their color and then their brightness:
private double GET_BRIGHTNESS_SLOW(Bitmap processedBitmap)
{
double Result = 0;
double brg = 0;
for (int x = 0; x < processedBitmap.Width; x++)
{
for (int y = 0; y < processedBitmap.Height; y++)
{
brg = processedBitmap.GetPixel(x, y).GetBrightness();
if (brg >= BORDER)
Result += brg;
counter++;
}
}
return Result;
}
The second algorithm is using the LockBits method and unsafe code:
private double GET_BRIGHTNESS(Bitmap processedBitmap)
{
double Result = 0;
double brg = 0;
unsafe
{
BitmapData bitmapData = processedBitmap.LockBits(new Rectangle(0, 0, processedBitmap.Width, processedBitmap.Height), ImageLockMode.ReadWrite, processedBitmap.PixelFormat);
int bytesPerPixel = System.Drawing.Bitmap.GetPixelFormatSize(processedBitmap.PixelFormat) / 8;
int heightInPixels = bitmapData.Height;
int widthInBytes = bitmapData.Width * bytesPerPixel;
byte* PtrFirstPixel = (byte*)bitmapData.Scan0;
for (int y = 0; y < heightInPixels; y++)
{
byte* currentLine = PtrFirstPixel + (y * bitmapData.Stride);
for (int x = 0; x < widthInBytes; x = x + bytesPerPixel)
{
int Blue = currentLine[x];
int Green = currentLine[x + 1];
int Red = currentLine[x + 2];
brg= Color.FromArgb(Red, Green, Blue).GetBrightness();
if (brg >= BORDER)
Result += brg;
counter++;
}
}
processedBitmap.UnlockBits(bitmapData);
}
return Result;
}
For comparison I wrote the following Code:
Stopwatch sw = new Stopwatch();
sw.Start();
double result = GET_BRIGHTNESS(p_BMP);
sw.Stop();
MessageBox.Show("Counter: " + counter.ToString() + "\r\nTime: " + sw.ElapsedMilliseconds + " ms \r\nValue: " + Math.Round(result, 2).ToString());
counter = 0;
sw.Reset();
sw.Start();
double result_sl = GET_BRIGHTNESS_SLOW(p_BMP);
sw.Stop();
MessageBox.Show("Counter: "+counter.ToString()+"\r\nTime: " + sw.ElapsedMilliseconds + " ms \r\nValue: " + Math.Round(result_sl, 2).ToString());
The result is for the fast version:
<br />
Counter: 325546<br />
Time: 24 ms<br />
Value: 14437,37<br />
and for the slow version:
<br />
Counter: 325546<br />
Time: 449 ms<br />
Value: 16367,6<br />
The Pictures Size is 659 x 494, so 325546 px, thats correct for both. The results above are for
BORDER = 0.25
. If i set
BORDER = 0
I get:
for the fast version
Value: 50220,87
and for the slow version
Value: 50239,4
Where does this difference come from? Obviously I want to have to correct value and the fast code... Does anyone have an Idea?