声纹识别_加入噪声

目录

      • 1、add noise to audio clips
        • signal to noise ratio(SNR)
      • 2、加入 additive white gaussian noise(AWGN)
        • 1. how to generate AWGN
        • 2. AWGN的频率分析
        • 3. 加入噪声
      • 3、加入 real world noises

1、add noise to audio clips

学习如何将噪声加入到audio data中,后续可以将不同SNR的噪声加入原始信号样本,评估不同噪声条件下的模型性能
首先读取原始audio.wav(里面是一段话:“leave my dog alone”)

import librosa
signal, sr = librosa.load(“path/to/audio.wav”)

绘制信号图:

import matplotlib.pyplot as plt
plt.plot(signal)

声纹识别_加入噪声_第1张图片

signal to noise ratio(SNR)

声纹识别_加入噪声_第2张图片
RMS是均方根
计算信号的RMS:

import numpy as np
RMS=math.sqrt(np.mean(signal**2))

dB = 20 × log ⁡ 10 ( RMS ) \text{dB} = 20 \times \log_{10}(\text{RMS}) dB=20×log10(RMS)

2、加入 additive white gaussian noise(AWGN)

1. how to generate AWGN

在这里插入图片描述
噪声是服从高斯分布,均值为0,标准差是 R M S n o i s e RMS_{noise} RMSnoise

noise=np.random.normal(0, STD_n, signal.shape[0])
# np.random.normal() 函数用于生成服从正态分布的随机数
# 生成一个形状与输入信号(signal)相同的数组,其中每个元素都服从均值为 0、方差为 STD_n 的正态分布。

生成的噪声图:
声纹识别_加入噪声_第3张图片

2. AWGN的频率分析

使用快速傅里叶变化来分析噪声的频率部分

X=np.fft.rfft(noise)
radius,angle=to_polar(X)

声纹识别_加入噪声_第4张图片
频率分布非常平稳,符合“白”的特征

3. 加入噪声
signal_noise = signal+noise

SNR=10dB
声纹识别_加入噪声_第5张图片
加入噪声的完整代码

#SNR in dB
#given a signal and desired SNR, this gives the required AWGN what should be added to the signal to get the desired SNR
def get_white_noise(signal,SNR) :
    #RMS value of signal
    RMS_s=math.sqrt(np.mean(signal**2))
    #RMS values of noise
    RMS_n=math.sqrt(RMS_s**2/(pow(10,SNR/10)))
    #Additive white gausian noise. Thereore mean=0
    #Because sample length is large (typically > 40000)
    #we can use the population formula for standard daviation.
    #because mean=0 STD=RMS
    STD_n=RMS_n
    noise=np.random.normal(0, STD_n, signal.shape[0])
    return noise
#***convert complex np array to polar arrays (2 apprays; abs and angle)
def to_polar(complex_ar):
    return np.abs(complex_ar),np.angle(complex_ar)
 #**********************************
#*************add AWGN noise******
#**********************************
signal_file='/home/sleek_eagle/research/emotion/code/audio_processing/signal.wav'
signal, sr = librosa.load(signal_file)
signal=np.interp(signal, (signal.min(), signal.max()), (-1, 1))
noise=get_white_noise(signal,SNR=10)
#analyze the frequency components in the signal
X=np.fft.rfft(noise)
radius,angle=to_polar(X)
plt.plot(radius)
plt.xlabel("FFT coefficient")
plt.ylabel("Magnitude")
plt.show()
signal_noise=signal+noise
plt.plot(signal_noise)
plt.xlabel("Sample number")
plt.ylabel("Amplitude")
plt.show()

3、加入 real world noises

将有噪声的音频加入到原始音频中
我们需要计算原始音频的RMS和噪声音频的RMS,为了能得到规定的SNR,我们需要修改噪声的RMS值,办法就是将每个噪声元素都乘上一个常数,这样就能使得噪声的RMS值也乘上一个常数,达到需要的噪声RMS。
在这里插入图片描述
噪声音频(水流的声音):
声纹识别_加入噪声_第6张图片
加入噪声的音频:
To listen to the signal and noise I used and also to the noise-added audio files that were created by adding noise to the signal, go to

#given a signal, noise (audio) and desired SNR, this gives the noise (scaled version of noise input) that gives the desired SNR
def get_noise_from_sound(signal,noise,SNR):
    RMS_s=math.sqrt(np.mean(signal**2))
    #required RMS of noise
    RMS_n=math.sqrt(RMS_s**2/(pow(10,SNR/10)))
    
    #current RMS of noise
    RMS_n_current=math.sqrt(np.mean(noise**2))
    noise=noise*(RMS_n/RMS_n_current)
    
    return noise
#**********************************
#*************add real world noise******
#**********************************

signal, sr = librosa.load(signal_file)
signal=np.interp(signal, (signal.min(), signal.max()), (-1, 1))
plt.plot(signal)
plt.xlabel("Sample number")
plt.ylabel("Signal amplitude")
plt.show()

noise_file='/home/sleek_eagle/research/emotion/code/audio_processing/noise.wav'
noise, sr = librosa.load(noise_file)
noise=np.interp(noise, (noise.min(), noise.max()), (-1, 1))


#crop noise if its longer than signal
#for this code len(noise) shold be greater than len(signal)
#it will not work otherwise!
if(len(noise)>len(signal)):
    noise=noise[0:len(signal)]

noise=get_noise_from_sound(signal,noise,SNR=10)

signal_noise=signal+noise


print("SNR = " + str(20*np.log10(math.sqrt(np.mean(signal**2))/math.sqrt(np.mean(noise**2)))))

plt.plot(signal_noise)
plt.xlabel("Sample number")
plt.ylabel("Amplitude")
plt.show()

参考链接:click here

你可能感兴趣的:(声纹识别,机器学习,人工智能,学习,语音识别)