Python | librosaを用いて曲のテンポを一覧化してみる(水樹奈々 / The Museum)

Python | librosaを用いて曲のテンポを一覧化してみる(水樹奈々 / The Museum)

みなさん、こんにちは。

今回は、前回の記事を元に 楽曲のテンポを一覧化してみて、その精度を見てみたいと思います。

今回の対象

自宅のCDを漁った結果、「水樹奈々」さんの「The Museum」を利用します。

プログラム

プログラムのカレントディレクトリに「THE_MUSEUM」というフォルダを作成し、その中に楽曲のmp3ファイルを置きました。

ビート解析のプログラムは以下の通りです。

import librosa
import librosa.display 
import os

dir_path = "THE_MUSEUM"
files = os.listdir(dir_path)

for mp3_file in files:
    y, sr = librosa.load(os.path.join(dir_path, mp3_file)) 
    tempo, beats = librosa.beat.beat_track(y=y, sr=sr)
    print(mp3_file + "," + str(tempo))

計算結果

結果を見てみます。今回は実際の精度を比較するため、自身でタップしたテンポも横に記載し、右端列には差を記載しています。

このことから、上位4曲が大幅にずれていることが分かります。

ETERNAL_BLAZEがなぜずれたか?

offset=15とし、Aメロ部分から30secを切り出しています。

Eternal blazeの場合、tempo=78 ぐらいの間隔でクラッシュ音が入っていることが分かります。

これに引っ張られて、テンポが正確に出なかったのではないか?と考えました。

import librosa
import librosa.display 
import IPython.display
import os

dir_path = "THE_MUSEUM"
files = os.listdir(dir_path)

y, sr = librosa.load(os.path.join(dir_path, 'eternal_blaze.mp3'),offset=15,duration=30) 
tempo, beats = librosa.beat.beat_track(y=y, sr=sr)

#------------------------------------------------------------
# クリック音を追加して再生
#------------------------------------------------------------
clicks = librosa.clicks(frames=beats, sr=sr, length=len(y))
IPython.display.Audio(data= y + clicks, rate=sr)
print(tempo) # 78.30255681818181

物は試しに、上記クラッシュ音が比較的出ていない offset=60秒から30秒間を切り出してみます。

import librosa
import librosa.display 
import IPython.display
import os

dir_path = "THE_MUSEUM"
files = os.listdir(dir_path)

y, sr = librosa.load(os.path.join(dir_path, 'eternal_blaze.mp3'),offset=60,duration=30) 
tempo, beats = librosa.beat.beat_track(y=y, sr=sr)

#------------------------------------------------------------
# クリック音を追加して再生
#------------------------------------------------------------
clicks = librosa.clicks(frames=beats, sr=sr, length=len(y))
IPython.display.Audio(data= y + clicks, rate=sr)
print(tempo) #151.99908088235293

テンポが151となり、原曲に近しいテンポを算出できました。

このことから、ピーク音の処理やオフセットなどを適切に行うことで精度を上げられる可能性があると分かりました。

実験

これといった正解のやり方は導けていませんが、実験として「beat_track」を用いて「harmonic部分」と「percussive部分」に分け、それぞれに対してテンポ解析にどのような差が出るかを見てみます。

比較対象として「原曲」も加えて、3パターンでのリズム抽出を行いました。

import librosa
import librosa.display 
import os

dir_path = "THE_MUSEUM"

files = os.listdir(dir_path)

for mp3_file in files:

    y, sr = librosa.load(os.path.join(dir_path, mp3_file)) 
    y_harmonic, y_percussive = librosa.effects.hpss(y)
    tempo, beats = librosa.beat.beat_track(y=y, sr=sr)
    tempo_harmonic, beats_harmonic = librosa.beat.beat_track(y=y_harmonic, sr=sr)
    tempo_percussive, beats_percussive = librosa.beat.beat_track(y=y_percussive, sr=sr)
        print(mp3_file + "," + str(tempo) + "," + str(tempo_harmonic) + "," + str(tempo_percussive))

結果は以下の通りになりました。

原曲でワースト4の曲は、harmonicのみで処理することである程度の改善が見られました。

しかし、下表のように harmonicもpercussiveも悪化している曲もあり、一長一短な結果となりました。

今回は リズム算出のプログラムを発展させて、どんなことが出来るかを検証してみました。

まだまだ精度が低いですが、楽曲の解析にも利用できそうですね!

ではまた!

本日のAmazonおすすめ_Top10

2024-04-29 06:30:47時点