sklearn是python的一个ML库。其文档非常详细,详细程度可称教材级别。使用简便。
音频输入==>STFT==>寻峰==>泛音提取==>使用sklearn进行聚类==>输出
本应用中由于输入的音频文件为44k的CD采样率,因此采用的STFT使用44100的原采样率,不再重新采样。并使用8000点的帧长度,步进2000点(即帧重叠6000点),使用hanning窗,以达到足够高的频率分辨度同时足以显示出乐曲的动态变化。
详细: XXXXXXXXXXXXXXXXXXXXXXXX/t/78789
这里没有使用特别复杂的寻峰算法,只是最简单的二阶导数+阈值
乐音中各次泛音成分的比例关系反映了声音的音色特征。因此提取前n次泛音与基频的比例,取对数(消除距离不均)后放入n维向量中进行聚类。由于高次数的泛音十分弱,易被噪音干扰,所能提供的特征信息也不多,因此n过大反而不利于分类。经多次测试,n的取值应在4附近,效果比较理想。 同时,由于和弦结构会对泛音产生一定干扰(例如,其中五度音程的两个音,二、三次泛音将会重叠在一起),因此应使用尽量简单的乐曲。
聚类使用sklearn库的SpectralClustering算法。样本应采用乐器种类较多,音色差别较大的乐曲,经实际测试,对部分乐器种类较少的乐曲分类效果不好。n_clusters的值应按照实际音色种类选择。
这几张图是各种测试参数的结果中效果比较好的几张。 泛音向量维度 3~5 n_clusers 5~7
fig.35 fig.30 fig.29 fig.27
从散点图中可看出,由于过于简单的寻峰算法,导致较弱的音丢失严重(例如最开头一段),较强的部分噪音比较严重(例如fig.36后部) 图中总体上还是能够反映出乐曲中各种乐器的使用情况的。
测试音频:
StarSky.mp3 5.11MB立即下载
mp3格式,请转换成wav后使用。(linux用户请使用mpg123而不是mpg321,python的wave库似乎无法读取mpg321所转换出的wav格式。。。。然而使用ubuntu的音乐播放器,视频播放器和octave读取都完全正常)
代码:XXXXXXXXXXXXXXXXXX/gym487/MLProj/
按规定论坛上传一份:
[修改于 8年5个月前 - 2016/08/08 16:06:39]
这个好玩,做了STFT以后对音乐的处理跟图像处理很像了。
回想起以前为了交作业抓学音乐的同学帮忙手动分析泛音的事了,因为坐标系的缘故,这里的图跟楼主在频率上是上下颠倒的。
看了一下代码,用的好像应该是 spectral clustering? DBSCAN 是不用预先知道需要分的cluster的数目。另外我在想,这个的 Feature selection 除了基于已有音乐知识,选择用泛音基频比例,有没有可能试试用PCA之类的方法盲处理? 我也想好好想一下,有脑洞了再来回复。
还有一个就是,如果改用supervised learning 来对不同乐器成分进行分类,对一段音乐的ground truth标记有什么比较好的解决方法?我现在能想到的只有用乐谱或者同一首曲目的MIDI文件。
引用 琪露诺:DBSCAN是笔误,已改。
这个好玩,做了STFT以后对音乐的处理跟图像处理很像了。
回想起以前为了交作业抓学音乐的同学帮忙手动分析泛音的事了,因为坐标系的缘故,这里的……
时段 | 个数 |
---|---|
{{f.startingTime}}点 - {{f.endTime}}点 | {{f.fileCount}} |
200字以内,仅用于支线交流,主线讨论请采用回复功能。