使用Python对一维信号进行基于小波的去噪处理
小波是一种应用于处理数字信号和压缩的函数。小波将高分辨率的信号转换为近似的详细系数。
近似系数是低分辨率的近似值,因为它们不显示变化的内容。另一方面,详细系数显示了变化,并使得从近似系数中恢复原始图像成为可能。
在本教程中,我们将看到如何进行一维信号的小波变换。此外,我们将看看用于这种分析的各种软件包、命令以及如何在应用中使用这种命令的例子。
前提条件
要跟上本教程的进度,读者应该具备以下条件。
噪声模型
信号在传输到一定距离时,经常会受到噪声的污染。加性噪声是获取噪声的最简单的模型。加性噪声是一种不需要的信号,它与真正的原始信号有关系。加性噪声有如下形式。
f'k = f(k) + n(k)
其中。
- f'(k)。是被污染的信号。
- f(k)。是原始信号。
- n(k)。是噪声信号。
噪声信号的基本假设是。
- 噪声是加性的。
- 噪声是一个随机信号(均值为 "零 "的白高斯噪声)。
- 噪声是一个高频信号。
这里的目标是使用小波变换技术从噪音音频信号(f'(k))中去除噪音(n(k))。这里使用的方案如下所示。

首先,信号被分解为上述图像中的详细和近似系数。然后,这些系数被阈值化,并对阈值化的系数进行反小波变换。
阈值化是一种非线性技术,对每个小波系数都有相应的操作。最后,进行反小波变换以得到原始信号。
我们在设置阈值时使用了诸如通用阈值、贝叶斯和Sure minimax等方法。
Scikit-image python包
这个包提供了灵活的图像处理的程序。它是用python语言编写的。此外,它有一个函数库,用于修复基于小波的去噪。
虽然它主要适用于二维图像,但它也可以用于一维信号。好消息是,scikit 图像包在anaconda中已经有了;因此,不需要安装它。
Scikit 小波去噪包括两个主要函数。这些函数是 和 。estimate_sigma() denoise_wavelet()
对于阈值的估计,只有两种支持的方法。
- 通用阈值(VishuShrink)。
- Bayes Shrink(这是默认方法)。
默认情况下,Denoise_wavelet() 函数被用于图像。然而,在本教程中,我们将把它用于一维信号,也就是说,与图像有关的其他属性被放弃。使用这个函数的语法是。
y = denoise_wavelet(x, wavelet='db1', mode='soft', wavelet_levels=n, method='BayesShrink', rescale_sigma='True')
其中。
x:是输入的噪声信号。y:是去噪后的输出。wavelet:这是使用的小波的名称。mode:使用的阈值处理模式。有两种阈值处理模式,即软阈值和硬阈值。wavelet_levels:分解级别。注意,这必须是一个整数。method:使用的阈值处理方法。这里我们使用两种支持的方法中的任何一种,即VishuShrink和BayesShrink。rescale-sigma:只有两个选项。这些选项是True或false。对于一维信号,应设置为true。如果是内部重新缩放的噪声方差信号,它是要重新缩放的。
对心电图(ECG)信号去噪
我们需要为这个程序安装numpy,PyWavelets,skimage, 和matplotlib 。我们可以使用pip 来安装这些软件包,如下所示。
# For numpy package.
pip install numpy
# For pywavelet package.
pip install pywavelet
# For matplotlib
pip install matplotlib
# Install scikit-image
python -m pip install -U scikit-image
这些安装命令在终端执行。然后将它们导入到代码中,如下图所示。
import numpy as np
import PyWavelets as pywt
from skimage.restoration import denoise_wavelet
import matplotlib.pyplot as plt
numpy包处理对数组的数学和逻辑操作。pywt包对输入信号进行小波变换。然后我们从skimage包中导入denoise_wavelet()函数。skimage包能够执行信号预处理程序。- 最后,对于Python中的任何绘图,都要使用
matplotlib包。
从内置的数据库中读取数据。Python有一个内置的ecg数据库。这使得它更有效率,因为我们不需要来自外部的数据。为了读取这些数据,我们使用下面的代码。
x = pywt.data.ecg().astype(float)/256 # In-built ecg data is read
从数据库中获得的信号是无噪音的。我们需要向其添加噪声以进行去噪操作。为了添加噪声,我们首先定义噪声方差。噪声方差是每个样本的噪声能量。
sigma = 0.05 # Noise variance
x_noisy = x + sigma * np.random.randn(x.size) # Adding noise to signal
为了向我们的信号(x)添加噪声,我们使用公式x + sigma * np.random.randn(x.size) 。
randn() ,考虑到噪声方差,添加一个随机噪声sigma 。
现在让我们使用denoise_wavelet() 函数进行小波去噪,使用前面描述的语法,如下图所示。
# Wavelet denoising
x_denoise = denoise_wavelet(x_noisy, method='BayesShrink', mode='soft', wavelet_levels=3, wavelet='sym8', rescale_sigma='True')
我们绘制出噪声信号x_noisy 和去噪信号x-denoise ,以便可视化。
plt.figure(figsize=(20, 10), dpi=100)
plt.plot(x_noisy)
plt.plot(x_denoise)
plt.show()
在绘图时,我们首先使用plt.figure() 函数创建一个图形。这个图的大小为20x10像素,如函数属性figsize 所述。
接下来,使用plt.plot() 函数将噪声信号和去噪信号绘制在准确的图中。代码片断plt.show() ,用来显示绘图的输出。该图的输出如下所示。

蓝色的信号是有噪声的ECG信号,红色的是去噪的信号。现在让我们来看看如何对音频信号进行去噪,因为它也是一个一维信号的样本。
对音频信号进行去噪
第一步是导入我们要使用的库。我们导入的这些库是用终端的pip 命令安装的,如下图所示。
pip install scipy
pip install numpy
pip install skimage
pip install matplotlib
scipy 包解决了你的程序的数学和科学计算。numpy 用于处理数组,matplotlib 绘制输出,而skimage 包则用于图像预处理程序,如前所述。
from scipy.io import wavfile
import numpy as np
from skimage.restoration import denoise_wavelet
import matplotlib.pyplot as plt
我们从scipy.io 中导入wavfile ,以读取.wav 格式的音频信号。由于涉及到一些数值运算,我们导入numpy 。我们还导入了denoise_wavelet() 函数和matplotlib.pyplot 。
然后我们使用wavfile.read() 函数读取音频文件,并将振幅归一化,如下所示。
Fs, x = wavfile.read('guitar.wav') # Reading audio wave file
x = x/max(x) # Normalizing amplitude
guitar.wav 文件应该和你的Python项目在同一个文件夹里,所以从这里下载这个吉他文件。信号样本将被储存在x 变量中,采样频率将被储存在Fs 变量中。
振幅是正常化的,因为wavfile 是以int16 模式读取音频的。这个模式给出的值很大。因此,我们需要通过归一化来减少这些值。
由于音频信号没有噪音,我们添加噪音,与我们对心电图信号所做的类似。
sigma = 0.05 # Noise variance
x_noisy = x + sigma * np.random.randn(x.size) # Adding noise to signal
# Wavelet denoising
x_denoise = denoise_wavelet(x_noisy, method='VisuShrink', mode='soft', wavelet_levels=3, wavelet='sym8', rescale_sigma='True')
加入随机噪声后,我们使用denoise_wavelet() 函数对信号进行去噪。这里,我们使用VishuShrink 方法。为了直观起见,我们绘制输出。
plt.figure(figsize=(20, 10), dpi=100)
plt.plot(x_noisy)
plt.plot(x_denoise)
plt.show()

蓝色的信号是噪声信号,而橙色的是去噪后的输出。所以很难知道去噪是否已经完成。然而,这可以通过计算峰值信噪比(PSNR)或实际听音乐来完成。
我们需要将sounddevice python软件包添加到anaconda中,以聆听音频。这可以在终端使用conda 或pip 包管理器来完成,如下图所示。
- 使用 pip
python3 -m pip install sounddevice
- 使用Conda
conda install -c conda-forge python-sounddevice
我们使用下面的代码片断来导入sounddevice 包。
import sounddevice as sd
一旦你导入了这个包,我们就可以通过在终端执行下面的命令来播放信号。
sd.play(x_noisy, Fs)
在这里,我们使用sd.play() 函数。这个函数把信号和采样频率作为参数。当我们播放噪声信号时,我们会发现背景中有一个噪声。
我们对去噪后的音频信号进行同样的操作,以获得差异。要听去噪后的音频信号,请执行下面的代码。
sd.play(x_denoise, Fs)
结论
python去噪的一维信号很容易。Python有操作库;因此,在这个过程中使用了一些代码片段。
去噪信号在科学和技术中是必不可少的。它也适用于安全领域和信号的增强和修改。