那些细碎的所得(1):有关音频特征处理

缘起

在学AI,当做各种特征工程的过程中,需要一个笔记来记录所得,不然以后遇到相同情况的时候,要参考各种文档还需要左查右查太繁琐了,不如记录下来,分享在博客,大家也能一起受益。

故,这个系列产生了。对于没有需要的人来说可能碎碎念,自用为主,各取所需啦。

处理音频特征需要库

import wave 
import numpy as np 
import scipy.signal as signal
import matplotlib.pyplot as plt  
  • 这里wave库是python自带,不用另外pip安装
  • numpy处理数组
  • signal是scipy库里面专门用于信号处理的
  • matplotlib用于特征可视化
  • 还有一个库叫做thinkdsp,是做数字信号处理的库,去github可以下载:GIThub里面的thinkdsp链接,还有电子书
  • 也可以通过下面的方法安装在自己库中,pip或者conda请随意
pip install thinkx
conda install thinkx
- 里面有thinkdsp处理音频信号的,也有thinkbayes贝叶斯相关的模块;
- 调用thinkdsp的方法: import thinkdsp
- 使用这个库处理音频也非常简便,具体参考Allen B. Downey的书;
- pypi有具体介绍:https://pypi.org/project/thinkx/

音频读取及查看参数

wavfile = wave.open("./data.wav", "rb")
# 后面记得 wavfile.close() 完成打开和关闭的过程

params = wavfile.getparams()
nchannels, sampwidth, framerate, nframes = params[:4]
  • params就是参数,这里涉及:
    • 有n声道(nchannels);
    • 量化位数(sampwidth,单位是byte);
    • 采样率(framerate);
    • 采样点数 (nframes)。

用numpy处理数据

# 读采样点形成datawav
datawav = wavfile.readframes(nframes)
# 用np.frombuffer是将1维音频向量翻译成数据data
# np.short是短整形数据格式,其实如果不选,也就是float浮点数格式
data = np.frombuffer(datawav, dtype = np.short)
# 专门转一次32位浮点数,方便后面喂数据
data = data.astype(np.float32) 

音频数据(特征可视化)

# numpy.linspace(start, stop, num=50, endpoint=True, retstep=False, dtype=None, axis=0) 
# 意思是在开始和结束之间返回均匀间隔的数据,准备作为时间X轴的度量
reftime = np.linspace(start=0, stop=nframes/framerate, num=nframes)

# 这里dpi设置画布分辨率
fig = plt.figure(1, figsize=(12, 8), dpi=100) 

gs = grid.GridSpec(2, 1) 

# 第一个图直接看音频data的样子
ax = fig.add_subplot(gs[0, 0]) 
ax.plot(reftime, data)
ax.set_xlim((np.min(reftime), np.max(reftime))) # 设置x窗

# 第二个图用短时傅里叶变换(STFT)做特征
ax = fig.add_subplot(gs[1, 0]) 

# 见下面signal.stft()的解析
f, t, feq = signal.stft(data, framerate, nperseg=1024, noverlap=1024-256)

feature =  np.log(np.abs(feq)+1) # 声音的特征
feature1d = np.reshape(feature, [-1]) # 展成1维形成特征
x = feature1d - np.mean(feature1d) # 去均值,整体值减去均值
x = x / (np.std(x) + 1e-6)         # 数据标准化,这里加一个极小值1e-6可以避免被除数为0

# pcolormesh就是频谱图(声音特征图)
ax.pcolormesh(t, f, np.log(np.abs(feq)+1))

plt.show()

短时傅里叶变换具体可参考如下博客:https://blog.csdn.net/fate_mt/article/details/104728797/
- 这一篇CSDN博客讲的也不错,有公式推导

scipy.signal.stft函数:具体输入参数

scipy.signal.stft(x,fs = 1.0,window =‘hann’,nperseg = 256,noverlap = None,nfft = None,detrend = False,return_oneside = True,boundary =‘zeros’,padded = True,axis = -1 )

参数:

  • x: STFT变换的时域信号
  • fs: 时域信号的采样频率
  • window: 时域信号分割需要的窗函数,可以自定义窗函数
  • nperseg: 窗函数长度
  • noverlap: 窗函数重叠数,默认为50%。
  • nfft: FFT的长度,默认为nperseg。如大于nperseg会自动进行零填充
  • return_oneside : True返回复数实部,None返回复数。

输出:

  • f: 频率
  • t: 时间
  • Zxx: STFT时频数据(也是我们要的特征)

pcolormesh函数

这是matplotlib库里的热图包,具体可以参考matplotlib的文库。

结果图

那些细碎的所得(1):有关音频特征处理_第1张图片
下图就是我们切好的音频特征。

你可能感兴趣的:(AI学习)