# 音楽素材分離ライブラリ Spleeter を使ってみた

# はじめに
[Deezer Spleeter](https://github.com/deezer/spleeter)なるボーカル抜き出しライブラリを試してみた。
音声分離というと、位相反転させて、ボーカルだけ抜き出すのが主流(ちょっと時代遅れかも)な気がしますがドラムやベースなど色々と抜き出せるのがSpleeter。
そして無料です。
[iZotope RX7](https://www.izotope.com/en/products/rx.html) よりも分離できる楽器の数が多いそうです。RX7持ってないんですけどね・・・とりあえず気になったので使ってみました。

# 環境
- windows 10 Home Edition
- Jupyter Notebook (jupyter 1.0.0)
- Python 3.7.6
- pip 19.3.1 

## 導入

[Github](https://github.com/deezer/spleeter) にてデータが配布されているので、任意の方法でダウンロードしてください。
(私はZipでダウンロードしました。)



解凍して・・・
<img width="700" alt="SnapCrab_NoName_2020-6-23_21-59-39_No-00.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/635079/91bcfe37-fbde-e406-da09-0982b0d8e161.png">

「spleeter.opynb」を開きます。

デモで既にデータとコードが用意されているようです。
<img width="700" alt="SnapCrab_NoName_2020-6-23_22-3-2_No-00.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/635079/8452bc36-5a1d-0858-4ec9-6128a2b9c061.png">


pip install spleeterの場合は先に**[ffmpeg](https://ffmpeg.org/download.html)をインストールする必要があります。**
(windowsの場合は、手動で入れて環境変数のpathを通します。)
dindowsの検索窓に「環境変数」と入れて検索すると「システム環境の編集」が出てきますので、ffmpegを保存しているディレクトリのbinまでを登録します。
<img width="400" alt="SnapCrab_Cortana_2020-6-24_19-34-19_No-00.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/635079/0e4b0f21-087b-10db-f545-2beca50ddf19.png">



Spleeterをインストールします。

```py
pip install spleeter
```


## 実行

from IPython.display import Audioを実行し、
audio_example.mp3をAudioでインポートします。
再生ボタンが出てくるので再生します。

```py

from IPython.display import Audio
Audio('audio_example.mp3')
```

いかにもデモ～～～な感じの曲が流れますね。


### 使用できるコマンド

 - separate : オーディオを分離する
   - 2stems(ボーカルとインストの2分割)
   - 4stems(ボーカル/ベース/ドラム/その他の4分離)
   - 5stems(ボーカル/ベース/ドラム/ピアノ/その他の5分離)
 - train : 事前に用意した分離されたトラックで分離モデルをトレーニングする
 - evaluate : トレーニング済みモデルの評価をする

#### 2分離を試す
```py

%%time
!spleeter separate -i audio_example.mp3 -o output/


#Wall time: 21min 17s
#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
```

事前のトレーニングモデルをダウンロードするため、初回はかなり時間がかかるようです。
Tensorflowを用いたGPU処理を行えば[高速に処理できる](https://github.com/deezer/spleeter/wiki)そうです。
私はGPUはRadeonシリーズを使っており、RadeonでTensorflowを使う方法を調べていないのでCPU処理で行っています。


#### 4分離&5分離&16kHz拡張

```py
#末尾に -p spleeter:4stems or 5stems
spleeter separate -i audio_example.mp3 -o audio_output -p spleeter:4stems
spleeter separate -i audio_example.mp3 -o audio_output -p spleeter:5stems

#16kHzまでの分離を実行する場合(通常は11kHzまで)
spleeter separate -i audio_example.mp3 -o audio_output -p spleeter:2stems-16kHz
```

## 結果を視聴

ディレクトリ直下から /output/audio_example/
に2stemsであれば、vocals.wavとaccompaniment.wavが作成されます。

```py
Audio('output/audio_example/vocals.wav')
Audio('output/audio_example/accompaniment.wav')
```

オーディオで著作物なので結果がここに貼れないのがなんともですが・・・
きれいに抜き出せていますが、抜き出せている場所は抜き出してる感特有の感じでますね。

### 4分離ver

```py
%%time
!spleeter separate -i audio_example.mp3 -o output/ -p spleeter:4stems

Wall time: 27min 52s
INFO:spleeter:Downloading model archive https://github.com/deezer/spleeter/releases/download/v1.4.0/4stems.tar.gz
INFO:spleeter:Validating archive checksum
INFO:spleeter:Extracting downloaded 4stems archive
INFO:spleeter:4stems model file(s) extracted
INFO:spleeter:File output/audio_example/vocals.wav written succesfully
INFO:spleeter:File output/audio_example/drums.wav written succesfully
INFO:spleeter:File output/audio_example/bass.wav written succesfully
INFO:spleeter:File output/audio_example/other.wav written succesfully
```

ボーカル、ドラム、ベース、その他で別れてます！これはすごい


## 別オーディオデータでやってみる

気になる点は2つ

- デモは抜き出せて当たり前なので選んだ曲でやってみる
- 海苔波形で抜き出せるかやってみる

海苔波形できたらすごいですね。


### 選んだ曲で分割できるのか
きれいに分離できそうなレベルの音圧の曲[Eye-D & DJ Hidden - Battlefield VIP](https://djhidden.bandcamp.com/album/battlefield-vip)で試してみました。
昨今のストリーミングサイト、Youtube等で準拠されているラウドネス値に近い-14LUFSでマスタリングされている4曲目を使います。
<img width="700" alt="SnapCrab_NoName_2020-6-24_0-6-34_No-00.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/635079/01756e95-e6b2-78d6-49c3-947917fe9be1.png">



ボーカルは無いようなものなので、4分離を試してみました。

```py

Audio('battlefield_cut.mp3')
%%time
!spleeter separate -i battlefield_cut.mp3 -o output_battlefield/ -p spleeter:4stems

#Wall time: 20.1 s
#INFO:spleeter:File output_battlefield/battlefield_cut/vocals.wav written succesfully
#INFO:spleeter:File output_battlefield/battlefield_cut/drums.wav written succesfully
#INFO:spleeter:File output_battlefield/battlefield_cut/bass.wav written succesfully
#INFO:spleeter:File output_battlefield/battlefield_cut/other.wav written succesfully
```
処理時間は20秒でした。
初回にトレーニングデータをダウンロードしてしまえば、早いみたいですね。

デモ程ではないですが、上手に抜けてます！
ベースとドラムが特にすごいです


### 音圧MAXな曲(所謂海苔波形)でも分割できるのか

分離結果がないのも寂しいので、自分の曲でやってみます。
[Quark - Game Over](https://open.spotify.com/track/1zdgxmZ9som75GFBSzJj73?si=Ck_pKvRKR3O9waOyVCKV5w)で抜いてみました
相当ごちゃごちゃしてるので、音圧MAX状態も含めて抜けたらすごいと思います。

ガッツリ海苔波形です。
オーケストラ→スーパーソウ→盛り上がり部分までを選んでみました
<img width="700" alt="SnapCrab_NoName_2020-6-24_0-55-39_No-00.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/635079/89a6b0bd-c3cb-02db-4394-8c05dad23707.png">



#### 4分割実行

```py
%%time
Audio('gameover_cut.mp3')
Audio('gameover2mix_cut.mp3') #マスタリング前のデータ(not海苔波形)も一緒にテスト

!spleeter separate -i gameover_cut.mp3 -o output_gameover/ -p spleeter:4stems
!spleeter separate -i gameover2mix_cut.mp3 -o output_gameover2mix/ -p spleeter:4stems
```

想像よりかは海苔波形でも分離できてます！
[分離結果はここから落とせます](https://www.dropbox.com/sh/cndbpy752zlhrp0/AABt6lIEClI8wqSSKJjq7uQSa?dl=0)

波形同士打ち消し合う処理だとどうしても"海苔波形=抜き出し不可"のイメージがあるんですが、すごいですね。
otherはでも、ドラム、シンセ系が普通に混ざってますね。トレーニングデータの影響だと思いますが、Rideはドラムと認識されてない感じがします。
ボーカルも殆ど入ってないんですが、そうでないものも色々反応してます。
ベースは50Hz~オクターブ上100Hzくらいまで。EQでローパスした時とあまり変わらないですね。

海苔波形でないものもやってみましたが、流石にこちらのほうが精度は高いですね。
後で余裕があればトレーニングファイルを用意してトレーニングさせてみたいです。


# まとめ
- 割と手軽
- デフォルトのトレーニングデータでも結構よく抜き出せる
  - シンセサイザー等デジタルな音はデフォルトだとあまり判別されてない
- 処理はCPUでも十分速い（トレーニングデータを1回ダウンロードしてしまえば）