首先特别指出,本博客思路参考:如何在信号中添加指定信噪比的高斯白噪声,为何深度学习去噪研究采用高斯白噪声?,特此感谢!
- 根据信噪比的定义,SNR是信号功率与噪声功率比值的对数,即:
- 信号功率,利用方差可以事先计算出来,结合给定的SNR,可以求出噪声的功率。然后生成标准高斯噪声序列,再转换为我们所需要的噪声,具体代码如下所示:
%给灰度图像添加指定信噪比的噪声
%先计算信号的功率,再获得噪声的功率,然后生成一个标准高斯分布(均值为0,标准差为1)
%的噪声序列(和信号长度一样),再通过转换得到我们最终想要的高斯噪声.
function [X1_noise,noise]=get_SNR(X,SNR)
% X:原灰度图像,使用imread读入
% SNR:指定的信噪比
% X1_noise:添加噪声后的图像
% noise:所添加的噪声
X1=im2double(X); %只针对图像,可以换成X1=double(X)/255;
%figure;imshow(X1)
[m,n]=size(X1);
noise=randn(m,n);
noise=noise-mean2(noise); %均值为0,方差接近1
avg1=mean2(X1);
s1=0;
for i = 1:m
for j = 1:n
s1 = s1+(X1(i,j)-avg1)^2;
%s1 = s1+X(i,j)^2; %未考虑去除均值
end
end
signal_power=s1/(m*n);%信号平均功率
noise_variance=signal_power*10^(-SNR/10);
noise=sqrt(noise_variance)/std2(noise)*noise; %期望的噪声
X1_noise=X1+noise; %得到指定信噪比的灰度图像
%figure;imshow(X1_noise)
return
- 检查合成图像的信噪比是否符合要求,代码如下:
function SNR=check_SNR(signal,noise)
% signal:原灰度图像,使用imread读入
% noise:噪声
signal=im2double(signal); %归一化到0~1之间,可以换成signal=double(signal)/255;
[m,n]=size(signal);
avg1=mean2(signal);
s1=0;
for i = 1:m
for j = 1:n
s1 = s1+(signal(i,j)-avg1)^2;
%s1 = s1+signal(i,j)^2;
end
end
signal_power=s1/(m*n); %信号平均功率
[m1,n1]=size(noise);
avg2=mean2(noise);
s2=0;
for i = 1:m1
for j = 1:n1
s2 = s2+(noise(i,j)-avg2)^2;
% s2 = s2+noise(i,j)^2;
end
end
noise_power=s2/(m1*n1); %噪声功率
SNR=10*log10(signal_power/noise_power);
return
- 实例验证如下(SNR=10db):
X=imread('./lena.png'); %从当前文件夹读入
figure;imshow(X)
[X1_noise,noise]=get_SNR(X,10);
figure;imshow(X1_noise)
figure;imshow(noise)
SNR=check_SNR(X,noise)
原图:
加噪声后图像:
噪声:
计算出的结果:SNR=10.000