🎹

音源分離ツールSpleeterと音源MIDI変換ツールBasic-PitchをM1 MacBook Air上のDockerで動作させる

2023/07/22に公開

はじめに

楽曲をアナライズしたいとき、ボーカルの旋律とか、伴奏の最低•最高音は聴音しやすいものです。
ですが、、たとえばテンションを含む密集した和音のボイシングまで分解するのは、途方もなくしんどいです。もちろん訓練された能力と、それなりの時間も必要になります。
手元に楽器がない環境の人にとっては、なおさら難しいことです。

そこで補助的に機械学習ライブラリの力を借りて、能力や時間がない人でも、より良い音楽学習ができるようにすることは、音楽の文化に良い影響があると思います。

SpleeterとBasic-Pitchという二つの最高なライブラリが提供するコマンドラインツールを使うことで、音源をパート別に分離して、それぞれのパートをMIDIノートとして出力することができます。

それによって、リファレンス楽曲の分析自体に時間をかけることなく、本当の目的である解析、そして解析した後にどう昇華させるか考える。ということに主な時間を割くことができます。

また、楽器を演奏する技術がない人や、楽器を所有できない人であっても、自分のアイデアのままに様々な音色や、テンポ、アゴーギグ、ボイシング、リハーモナイゼーションを試すことができ、演奏ではなく音楽表現だけに取り組むことができます。

とまあ大義をふりかざしましたが、ただ自分がやってみたかっただけです。そしてやってみたので、その実行環境の構築内容を記録します。

ライブラリの紹介

Spleeterは、Vo./Dr./Ba./Pf./other の5パートまで対応できる、オープンソースの音源分離ライブラリです。
Basic-Pitchは、和音やピッチベンドに対応できる、オープンソースのオーディオ→MIDI変換ライブラリです。

ここでは各ライブラリの詳しい中身や、たくさんのオプション(パラメータの調整機能)については書かずに、動作環境を構築する部分だけを記載します。本当に素晴らしい資産なので公式ドキュメントを見てみてください。

そして実は、ただ試すだけであれば、今回の手順より簡単な方法があります。
SpleeterはGoogle collaborateryで実行環境を作ってくれているので、環境構築の手間がありません。
Basic-PitchはWeb GUIで誰でも簡単にできます。会員登録の必要もなく、何回やっても無料です。

じゃあなぜ下記の手順で構築するのかと言うと、大量のデータでも、オフライン環境でも、気にせず実行できるからです。ではとりあえずやっていきます。

環境

MacBook Air 2020
チップ Apple M1
macOS 13.0.1
メモリ 8GB

各ライブラリで要求されるpythonバージョンが異なる可能性があったことと、Linuxのamd64アーキテクチャ上の方が問題が少なそうだったため、Dockerでの仮想環境上に構築する前提で記載しています。
またコンソール出力は膨大なため、ほとんど記載は省略しています。

Dockerインストール

Docker環境の準備については、Docker公式から、Mac OSまたはWindows用のDocker Desktopをインストールするだけです。
この部分は、参照できるドキュメントが他にたくさんあるので、ここでは割愛します。

Spleeter

Linuxコンテナ作成

Dockerのインストールが完了したら、ターミナルからdockerコマンドを叩き、ubuntuイメージを取得します。(ここは直接runしても良いと思います)

$ docker pull ubuntu

ubuntuコンテナをバックグラウンドで起動します。

$ docker run -itd ubuntu /bin/bash

いま起動したコンテナに入ります。

$ docker exec -it a91ed /bin/bash --login
root@a91ed44bac86:/# 

Spleeterコンテナ構築

仕込みとして下記を一通り実行します。

root@a91ed44bac86:/# apt update
root@a91ed44bac86:/# apt -y upgrade
root@a91ed44bac86:/# apt install -y python3-pip
root@a91ed44bac86:/# python3 -m pip install --upgrade pip

pythonはあらかじめubuntuにインストールされているので、バージョンを確認しておきます。

root@a91ed44bac86:/# python3 -V
Python 3.10.6

3.10なんですね。Spleeterは3.8にしか対応していないという情報が多く見つかるんですが、2023年現在は対応してると書いてあったはずなので、気にせずに続けます。

ffmpegをインストールします

root@a91ed44bac86:/# apt install -y ffmpeg

spleeterをインストールします

root@a91ed44bac86:/# pip3 install spleeter

インストール後にspleeterコマンドを叩いてみます。パスが通っているのでOKです。

root@a91ed44bac86:/# spleeter             
Usage: spleeter [OPTIONS] COMMAND [ARGS]...

Options:
  --version  Return Spleeter version
  --help     Show this message and exit.

Commands:
  evaluate  Evaluate a model on the musDB test dataset
  separate  Separate audio file(s)
  train     Train a source separation model

次に、簡単に動作確認してみます。
起動時にボリュームをマウントしていなかったので、今は公式ドキュメントのチュートリアルの方法を使って音源を調達します。

root@a91ed44bac86:/# apt install -y wget
root@a91ed44bac86:/# wget https://github.com/deezer/spleeter/raw/master/audio_example.mp3

ダウンロードできました。今回とりあえず動かしたいだけなので、rootユーザのまま、ディレクトリも適当です。

root@a91ed44bac86:/# ls
audio_example.mp3  bin  boot  dev  etc  home  lib  media  mnt  opt  proc  root  run  sbin  srv  sys  tmp  usr  var

spleeterコマンドを実行します。うまく動きました!Python 3.10 でいけますね。Mac上だと依存関係のエラーでうまくいきませんでしたが、Linux上だと、いとも簡単に動作しました。感謝

root@a91ed44bac86:/# spleeter separate -p spleeter:2stems -o output audio_example.mp3
INFO:spleeter:Downloading model archive https://github.com/deezer/spleeter/releases/download/v1.4.0/2stems.tar.gz
INFO:spleeter:Validating archive checksum
INFO:spleeter:Extracting downloaded 2stems archive
INFO:spleeter:2stems model file(s) extracted
INFO:spleeter:File output/audio_example/accompaniment.wav written succesfully
INFO:spleeter:File output/audio_example/vocals.wav written succesfully

出力ファイルが収められたoutputと、事前学習済みモデルのpretrained_modelsディレクトリが作成されています。

root@a91ed44bac86:/# ls
audio_example.mp3  bin  boot  dev  etc  home  lib  media  mnt  opt  output  pretrained_models  proc  root  run  sbin  srv  sys  tmp  usr  var

outputの中身には、ボーカル音源と伴奏の音源が生成されています。やった。

root@a91ed44bac86:/# ls /output/audio_example/
accompaniment.wav  vocals.wav

うまく動くことがわかったので、このコンテナをイメージ化しておきたいと思います。
一旦コンテナから抜けます。

root@a91ed44bac86:/# exit
logout

Spleeterイメージ作成

さっきまで入っていたコンテナの情報を確認します。

$ docker ps
CONTAINER ID   IMAGE     COMMAND       CREATED          STATUS          PORTS     NAMES
a91ed44bac86   ubuntu    "/bin/bash"   32 minutes ago   Up 32 minutes             amazing_carson

さっき構築したコンテナを元に「spleeter」という名前でイメージ化します。

$ docker commit amazing_carson spleeter

spleeterイメージが作成されました。

$ docker images
REPOSITORY        TAG          IMAGE ID       CREATED          SIZE
spleeter          latest       3ecff9ed843e   11 seconds ago   2.93GB
ubuntu            latest       37f74891464b   3 weeks ago      69.2MB

Spleeterコンテナ実行

次は、このspleeterイメージを起動させます。
今度はコンテナとファイルのやり取りができるようにしたいと思います。
とりあえず簡単にやりたいので、バインドマウントすることにします。
自分のPC上に、適当に共有用ディレクトリを作成して、パートを分離したい音源を置いておきます。

$ mkdir -p ~/docker/share
$ mv ~/Desktop/baby.wav ~/docker/share/

「baby.wav」としていることについて、
今回ボーカルと伴奏の2トラック音源の分離を試すために、babybaby/世武裕子さんの作品を使用しました。(銀杏BOYZのカバーで、ボーカルとピアノのみの美しく洗練されたアレンジが最高で、今回の分析•解析にぴったりです)

コンテナ内のマウントポイントに、いま作った共有ディレクトリを接続して、コンテナを起動します。

$ docker run -itd -v ~/docker/share:/mnt/share spleeter bash

コンテナに入ります。

$ docker exec -it f27c bash --login
root@f27cfaac2860:/#

共有ディレクトリに音源が入っています。うまくバインドマウントできているようです。

root@f27cfaac2860:/# ls /mnt/share/
baby.wav

spleeterコマンドを実行します。今回は共有ディレクトリ内に出力するように指定しました。

root@f27cfaac2860:/# spleeter separate -p spleeter:2stems -o /mnt/share/output/ /mnt/share/baby.wav 
INFO:spleeter:File /mnt/share/output/baby/vocals.wav written succesfully
INFO:spleeter:File /mnt/share/output/baby/accompaniment.wav written succesfully

共有ディレクトリにoutput/baby/が作成され、その中にボーカルと伴奏に分離された音源が生成されています。
聞いてみましたが、かなり綺麗に分離できています。
spleeter-result

Basic-Pitch

Linuxコンテナ作成

basic-pitchも使えるようにします。
まず、もう一度ubuntuコンテナを立ち上げて、basic-pitchコンテナを作成するところまでやります。

$ docker run -itd ubuntu /bin/bash

コンテナにログイン

$ docker exec -it 47d0 /bin/bash --login
root@47d0fb945608:/# 

Basic-Pitchコンテナ構築

仕込み作業

root@a91ed44bac86:/# apt update
root@a91ed44bac86:/# apt -y upgrade
root@a91ed44bac86:/# apt install -y python3-pip
root@a91ed44bac86:/# python3 -m pip install --upgrade pip

libsndfile1がないと動かないのでインストールします。

root@47d0fb945608:/# apt install -y libsndfile1

basic-pitchをインストールします。

root@47d0fb945608:/# pip install basic-pitch

インストールが終わったらパスが通っています。linux上だと楽ですね。mac上だとパスは自分で通す必要がありました。Windowsはやったことないけどなんかもっと大変みたいです。

root@47d0fb945608:/# basic-pitch
usage: basic-pitch [-h] [--model_path MODEL_PATH] [--save-midi] [--sonify-midi] [--save-model-outputs] [--save-note-events]
                   [--onset-threshold ONSET_THRESHOLD] [--frame-threshold FRAME_THRESHOLD] [--minimum-note-length MINIMUM_NOTE_LENGTH]
                   [--minimum-frequency MINIMUM_FREQUENCY] [--maximum-frequency MAXIMUM_FREQUENCY] [--multiple-pitch-bends]
                   [--sonification-samplerate SONIFICATION_SAMPLERATE] [--midi-tempo MIDI_TEMPO] [--debug-file DEBUG_FILE] [--no-melodia]
                   output_dir audio_paths [audio_paths ...]
basic-pitch: error: the following arguments are required: output_dir, audio_paths
root@47d0fb945608:/# exit
logout

Basic-Pitchイメージ作成

ここで一旦イメージ化します。

$ docker ps
CONTAINER ID   IMAGE      COMMAND       CREATED             STATUS             PORTS     NAMES
47d0fb945608   ubuntu     "/bin/bash"   7 minutes ago       Up 7 minutes                 elated_chaplygin
$ docker commit elated_chaplygin basic-pitch
$ docker images
REPOSITORY        TAG          IMAGE ID       CREATED          SIZE
basic-pitch       latest       10ecb120a3b9   27 seconds ago   2.43GB
spleeter          latest       3ecff9ed843e   2 hours ago      2.93GB
ubuntu            latest       37f74891464b   3 weeks ago      69.2MB

Basic-Pitchコンテナ実行

作成したbasic-pitchイメージからコンテナを起動します。

$ docker run -itd -v ~/docker/share:/mnt/share basic-pitch bash
$ docker exec -it 5d1b bash --login
root@5d1b9960c0d9:/# 

バインドマウントできています。

root@5d1b9960c0d9:/# ls /mnt/share/
baby.wav  output

basic-pitchコマンドを実行して、さっきSpleeterでボーカルを除去したピアノパートの音源を、MIDIデータに変換します。

root@5d1b9960c0d9:/# basic-pitch /mnt/share/output/baby/ /mnt/share/output/baby/accompaniment.wav 

✨✨✨✨✨✨✨✨✨
✨ Basic Pitch  ✨
✨✨✨✨✨✨✨✨✨

Importing Tensorflow (this may take a few seconds)...

Predicting MIDI for /mnt/share/output/baby/accompaniment.wav...


  Creating midi...
  💅 Saved to /mnt/share/output/baby/accompaniment_basic_pitch.mid

✨ Done ✨

うまく出力されました✨
basic-pitch-result

logicプロジェクトにインポートしてみると、かなり良い精度でMIDIノートに変換されています。
すごい!
logicprox

最後に

今回駆け足で紹介しましたが、オプションで細かくパラメータを調整できたりして本当に多機能です。
ぜひ公式ドキュメントを参照してください。

Discussion