How To Make Uniform Noise On Images – C# Guide
Uniform noise is one of the noise models we can use to simulate real life data corruption. This guide shows how to make in on images.
Filter by Category
Uniform noise is another one of the noise models we can use to simulate data corruption. As its name might suggest, this type of noise is distributed uniformly across a band of intensities. Furthermore, we will use probability distribution function to make it, as we do for all the other noise models.
We use noise models to find the best restoration and reconstruction techniques to remove noise from images. Therefore we need to simulate all sorts of models, as we encounter various different noise variation and distribution in acquired data.
In our case here, we will use this noise model on images. Whenever we take a photo, most common reasons for image noise are low grade equipment and environment condition. For example, if we use an old camera, which is more likely to be sensitive to temperature change and lightning, there’s a higher chance of getting a noisy image.
We will use a probability distribution function to distribute noise pixel intensity values. Formula is fairly simple, since it distributes among selected intensities evenly. Some authors also call this noise Quantization noise.
Let’s take a look at the following formulation of its probability distribution function.
Parameters a and b are essentially the intensity boundaries between which we distribute uniform noise PDF. In addition, let’s take a look at the following probability distribution graph that this function makes.
We will use the PDF to make an image histogram for our noise. After that we will dedicate equal amount of pixels for each intensity in the band. And finally, we will take all those values and scramble them to randomize their position on the noise image.
The following code does what we described above and adds the noise image values to the original image.
public static Bitmap UniformNoise(this Bitmap image)
{
int w = image.Width;
int h = image.Height;
BitmapData image_data = image.LockBits(
new Rectangle(0, 0, w, h),
ImageLockMode.ReadOnly,
PixelFormat.Format24bppRgb);
int bytes = image_data.Stride * image_data.Height;
byte[] buffer = new byte[bytes];
byte[] result = new byte[bytes];
Marshal.Copy(image_data.Scan0, buffer, 0, bytes);
image.UnlockBits(image_data);
byte[] noise = new byte[bytes];
double[] uniform = new double[256];
double a = 32;
double b = 64;
Random rnd = new Random();
double sum = 0;
for (int i = 0; i < 256; i++)
{
double step = (double)i;
if (step >= a && step <= b)
{
uniform[i] = (double)(1 / (b - a));
}
else
{
uniform[i] = 0;
}
sum += uniform[i];
}
for (int i = 0; i < 256; i++)
{
uniform[i] /= sum;
uniform[i] *= bytes;
uniform[i] = (int)Math.Floor(uniform[i]);
}
int count = 0;
for (int i = 0; i < 256; i++)
{
for (int j = 0; j < (int)uniform[i]; j++)
{
noise[j + count] = (byte)i;
}
count += (int)uniform[i];
}
for (int i = 0; i < bytes - count; i++)
{
noise[count + i] = 0;
}
noise = noise.OrderBy(x => rnd.Next()).ToArray();
for (int i = 0; i < bytes; i++)
{
result[i] = (byte)(buffer[i] + noise[i]);
}
Bitmap result_image = new Bitmap(w, h);
BitmapData result_data = result_image.LockBits(
new Rectangle(0, 0, w, h),
ImageLockMode.WriteOnly,
PixelFormat.Format24bppRgb);
Marshal.Copy(result, 0, result_data.Scan0, bytes);
result_image.UnlockBits(result_data);
return result_image;
}
This type of noise models is one of the easier to implement, since it doesn’t have complicated distribution across intenstities. You can also download the entire project that demonstrates what we described in this post.