表題のとおり,様々な拡張子に対応し,複数の楽曲ファイルを一括でNumpy配列に変換する関数です。
大量の音楽ファイルを分析する場合にオススメです。
ファイルの読み込みは librosa.load() を使っています。
librosa.load()
は引数にサンプリング周波数を与えることで,楽曲ファイルのサンプリング周波数と引数にサンプリング周波数が異なる場合,resampy でリサンプリングしてくれます。
ただし、リサンプリングは割と処理時間がかかるので注意が必要です*1。
librosa.load()
が扱いにくい場合は、PySoundFileを直接使うのがよいと思います。
# -*- coding: utf-8 -*- import os, sys import glob import librosa import numpy as np from pathlib import Path from itertools import chain from pprint import pprint def load_multiple_audio_files( dirpath, sr=44100, exts=[".wav", ".flac", ".mp3", ".m4a"], ): exts = exts + [_.upper() for _ in exts] if os.path.isdir(dirpath): p = Path(dirpath) filepath_list = list(chain.from_iterable([list(p.glob(f"*{ext}")) for ext in exts])) if len(filepath_list) < 1: print(f"the directory does not contain any audio files") return [], [] print(filepath_list) signal_list = [None for k in range(len(filepath_list))] for idx, filepath in enumerate(filepath_list): #filepath = os.path.normpath(filepath).replace("\\", "/") filepath = str(filepath) filename = os.path.splitext(os.path.split(filepath)[1])[0] try: y, _ = librosa.load(filepath, sr=sr, mono=False, offset=0, duration=None) except Exception as e: print("Error: can not load the audiofile:") print(f"\t{filepath}") print(f"\t{e}") return [], [] signal_list[idx] = y else: print("the directory is not exists:") print(f"\t{dirpath}") signal_list, filepath_list = [], [] return signal_list, filepath_list if __name__ == '__main__': dirpath = sys.argv[1] signal_list, filepath_list = load_multiple_audio_files(dirpath) import code console = code.InteractiveConsole(locals=locals()) console.interact()
*1:特に,48 kHz <=> 44.1 kHz のような補間係数/補完係数が大きくなる変換