题 如何在php中检测歌曲的BPM [关闭]


如何以编程方式确定歌曲的节奏/ BPM?常用的算法是什么,必须考虑哪些因素?


76
2018-03-18 05:32


起源




答案:


这在单个StackOverflow帖子中解释具有挑战性。通常,最简单的节拍检测算法通过定位声能中的峰值来工作,这很容易被检测到。使用更复杂的方法 梳状滤波器 和其他统计/波形方法。有关包含代码示例的详细说明,请检查 这篇GameDev文章 出。


42
2018-03-18 05:38



仅供参考,我知道这是一个旧帖子,但游戏开发文章给出了404 - avanderw
我会考虑到这一点,抱歉没有想到它,并试图提供更多信息而不是批评。 - avanderw
5年后,GameDev文章没有404ツ(除此之外你经常可以使用webarchive.org,按照 web.archive.org/web/20120525085210/http://archive.gamedev.net/... ) - earcam


要搜索的关键字是“节拍检测”,“节拍跟踪”和“音乐信息检索”。这里有很多信息: http://www.music-ir.org/

有一个(可能)年度比赛称为MIREX,其中不同的算法测试其节拍检测性能。

http://nema.lis.illinois.edu/nema_out/mirex2010/results/abt/mck/

这应该给你一个要测试的算法列表。

一个经典的算法是 Beatroot (google it),这很好,很容易理解。它的工作原理如下:

  1. 短时FFT音乐得到超声波图。
  2. 求和 增加 每个时间步长的所有频率的幅度(忽略减少)。这为您提供了称为“光谱通量”的一维时变函数。
  3. 使用任何旧的峰值检测算法查找峰。这些被称为“开始”并且对应于音乐中的声音开始(音符开始,鼓点击等)。
  4. 构建起始间隔(IOI)的直方图。这可用于查找可能的节奏。
  5. 为节拍跟踪结果初始化一组“代理”或“假设”。按顺序一次一个地添加这些代理。每个代理都跟踪也是节拍的开始列表,以及当前的速度估计。代理可以接受开始,如果它们与他们最后跟踪的节拍和节奏紧密相符,如果它们完全不同则忽略它们,或者如果它们介于中间则产生新的代理。不是每个节拍都需要一个发作 - 代理可以插入。
  6. 每个代理人根据其假设的整齐程度给出一个分数 - 如果其所有的节拍开始都是响亮的,则获得更高的分数。如果它们都是常规的,它会获得更高的分数。
  7. 最高得分代理就是答案。

根据我的经验,这个算法的缺点是:

  • 峰值检测非常临时且对阈值参数和诸如此类的敏感。
  • 有些音乐对节拍没有明显的影响。显然它不适用于那些。
  • 很难知道如何解决60bpm-vs-120bpm问题,尤其是实时跟踪!
  • 扔掉了 批量 仅使用1D光谱通量的信息。我估计你可以通过一些带限频谱通量(可能是一个宽带鼓通道)来做得更好。

这里 是该算法的实时版本的演示,显示光谱通量(底部的黑线)和开始(绿色圆圈)。值得考虑的是节拍是从中提取出来的 只要 绿色的圆圈。我已经播放到的突起,就像点击,说实话,我不认为我能听到他们的节奏,所以在某些方面该算法在拍子检测比人更好。我认为减少这种低维信号是它的弱点。

令人讨厌的是,几年前我确实找到了一个非常好的网站,其中包含许多用于节拍检测的算法和代码。我完全没有改过它。

编辑:发现它!

以下是一些很棒的链接,可以帮助您入门:

http://marsyasweb.appspot.com/

http://www.vamp-plugins.org/download.html


30
2018-03-27 15:30



很难为OSX目标构建Vamp插件。没有依赖关系的probem,但是使用了darwin的os typedef。在将sdk切换到... / Developer / SDKs / iPhoneOS7.0.sdk之后尝试make -f build / Makefile.osx以查看我的意思。 - loretoparisi


节拍提取涉及识别音乐中的认知度量结构。很多时候,这些不符合实际的声音能量 - 例如,在大多数的音乐有切分音的水平,这意味着“脚攻”击败我们认为不符合物理声音的存在。这意味着这是一个完全不同的领域 发病检测,这是物理声音的检测,并以不同的方式执行。

你可以尝试一下 Aubio library,这是一个普通的C库,提供起始和节拍提取工具。

还有在线 Echonest API虽然这涉及将MP3上传到网站并检索XML,但可能不太适合..

编辑: 昨晚我遇到了这个 - 一个非常有前途的C / C ++库,虽然我自己没有使用它。 鞋面插件


22
2018-03-18 07:56



你决定使用哪一个? - x.y


您感兴趣的一般研究领域称为MUSIC INFORMATION RETRIEVAL 

有许多不同的算法可以做到这一点,但它们都基本上以ONSET DETECTION为中心。

开始检测测量事件的开始,在这种情况下的事件是正在播放的音符。您可以查看加权傅立叶变换(高频内容)中的变化,您可以查看物质内容的较大变化。 (特殊差异)。 (我建议你进一步研究几篇论文)一旦你应用了一个起始检测算法,你就可以通过阈值来挑选节拍的位置。

一旦你获得节拍的时间定位,就可以使用各种算法。你可以把它变成一个脉冲串(创建一个信号,那就是零,所有时间和1只有当你的节拍发生)然后应用FFT到和BAM现在你有最大峰起始点的频率。

以下是一些引导您朝着正确方向前进的论文:

http://www.elec.qmul.ac.uk/people/juan/Documents/Bello-TSAP-2005.pdf

http://bingweb.binghamton.edu/~ahess2/Onset_Detection_Nov302011.pdf

以下是一些人正在讨论的内容的扩展:

有人提到寻找到应用机器学习算法:基本上收集从开始检测功能的一堆功能(如上所述),并与原始信号在神经网络/ logistic回归将它们结合起来,并了解是什么让一个节拍一个节拍。

看看Andrew Ng博士,他在线获得斯坦福大学的免费机器学习讲座(不是漫长的视频讲座,实际上是在线远程课程)


9
2018-03-13 20:43





如果您可以设法在项目中与python代码进行交互, Echo Nest Remix API 是一个非常漂亮的python API:

有一种方法 analysis.tempo 这将为您提供BPM。它可以比简单的BPM做得更多,正如您可以从API文档或 这个 教程


9
2018-03-18 06:18





执行一个 傅里叶变换,并找到功率谱中的峰值。您正在寻找低于20 Hz截止值的人类听觉峰值。我猜通常在0.1-5Hz的范围内是慷慨的。

这个问题可能会有所帮助: Bpm音频检测库

此外,这是关于SO的几个“高峰发现”问题之一: 测量信号的峰值检测


编辑: 不是我做音频处理。这只是基于你正在寻找文件的频域属性这一事实的猜测......


另一个编辑: 值得注意的是,有损压缩格式如mp3,首先存储傅里叶域数据而不是时域数据。有点聪明,你可以节省一些繁重的计算......但是看到cobbal的深思熟虑的评论。


7
2018-03-18 05:37



然而,mp3通过切断人类听觉之外的频率来实现压缩。傅立叶可能不是这里的正确工具。 - cobbal
啊。好的,那个。 - dmckee
MP3不会“切断”人类听觉之外的频率,它会分别对大约1毫秒宽的封闭窗口执行余弦变换(与傅里叶相关)。我会尝试dmckee在10秒长窗户上的第一个建议,看看会发生什么。 - TrayMan
这太简单了,不能真正运作良好。 - Timmmm


准确的BPM检测非常困难。看到 这个stackoverflow问题,以及我对它的回复。


2
2018-03-18 09:55





重新发布我的答案:简单的方法是让用户按节拍的节拍点击按钮,并计算点击数除以时间。


2
2018-03-20 21:46





其他人已经描述了一些节拍检测方法。我想补充说,有一些库可用于为这类任务提供技术和算法。

Aubio 是其中之一,它具有良好的声誉,它用C语言编写,带有C ++包装器,因此您可以轻松地将其与cocoa应用程序集成(Apple框架中的所有音频内容也使用C / C ++编写)。


2
2018-02-13 12:15





有几种方法可以获得BPM,但我发现最有效的方法是“拍频谱”(描述 这里)。 该算法通过将音乐的每个短样本与每个其他短样本进行比较来计算相似度矩阵。一旦计算出相似度矩阵,就可以获得每个时间间隔T的每个样本对{S(T); S(T + 1)}之间的平均相似度:这是拍频谱。拍频谱中的第一个高峰是节拍持续时间的大部分时间。最好的部分是你也可以做音乐结构或节奏分析等事情。


2
2018-02-23 23:16