前々から声質変換とか音声合成に興味があって「やりたいな~」と思っていたのですが、Diff-SVCという手法(?)がすごいのでやってみた、という記事です。
日本語どころか、英語でもあんまりドキュメントっぽいのが無いな~って感じなのでざっくり解説。
基本的な訓練の流れは公式のドキュメントを参照。
ここ→ training_and_inference_EN.markdown
必要なもの:
- VRAM24GB以上のGPU(訓練時)
24GBもねえよって人でもクラウドで借りればできるので、安心。今回自分はColaboratoryでやったので適当に参考にしてください。
ちなみに私はRTX 3070ユーザーです。
1. 学習データの収集
まず学習に使うデータ集め。1つの音声ファイルは5秒から15秒程度にするとよく、今はwav形式かogg形式がサポートされているようです。
音声データは目的となる話者の声のみが含まれていて、他の人の声やBGMなどが含まれていないものである必要があります。
学習データはトータルで3時間分程度(あるいはそれ以上)が推奨されています。
今回は適当な最近の雑談配信を3つくらい選んで(総データ量としては4.25時間分くらい、うち8割くらいを訓練に使用)使いました。
背景雑音の除去
配信の音声を学習データに用いるわけですが、当然そのままだと一般的にはBGMなどが含まれていると思うので、除去します。
今回はMetaからリリースされているDemucsというモデルを使いました。
音声分離をしたいだけならpip installするだけで使えるようになるので非常に便利です。
普通は歌の音源からボーカルや楽器などの音などの音を分離するために使う想定だと思いますが、BGMの除去にも使えます。しかも、結構高品質に声を抜き出せます。いい時代になりました。
音声分離に用いるモデルはいくつか選べるのですが、今回は標準の設定のまま(htdemucs
)にしました。ローカルでは音声1秒あたり1秒ちょっとで処理できるくらいのスピードで、学習データ全体の処理には4~5時間程度かかりました。まあ、ゲームとかして待ってればいいですね。
2. 学習済みモデルを準備する
Diff-SVCのリポジトリには必要なモデルは含まれてないので、自分で追加でダウンロードしてきます。
ここから0102_xiaoma_pe.zip
と0109_hifigan_bigpopcs_hop128.zip
をダウンロードします。Diff-SVCのディレクトリの中にcheckpoints
というディレクトリを作成して、解凍したモデルをそれぞれ入れておきます。
また、以下のリポジトリからHuBERT-Softのモデルをダウンロードしてこれもcheckpoints/hubert/
に保存しておきます。
3. 学習用の設定を変更する
公式のドキュメントを参考に、training
ディレクトリの中にあるconfig.yaml
を編集します。
今回はlearning rateなどはサンプルからパクりました。本当にそれでいいのか?
学習データやHuBERTなどのパスが正しいかちゃんと確認しておきましょう。
4. 学習データのプリプロセス
先程集めた生の学習データがそのまま訓練に用いられるわけではなく、前処理があります。何をしているのかは知りません。(?)
自分の環境では1時間弱くらいでした。飯食ったり風呂入ったりしてれば終わります。
5. 訓練(本編)
「VRAM8GBでもいけるかな~」と思っていたら、普通にOut of Memoryでダメでした。
Colabの無料枠のTesla T4(VRAM16GB)で耐えるかなあと思ったらこいつでも普通にOut of Memoryになったので、諦めて普通に課金。まあグラボ新しく買うよりは安いので……。
なんかGCPのCompute Engineの方が安上がり?みたいな説も聞いたのですが、訓練のコマンド1つ叩くためだけにVMのセットアップを1からやるのがめんどうで、普通にColabにしてしまいました。
初めてColab Proを使ったのですが、1ヶ月GPU使い放題なのかと思ったら流石にそんなことはなく、現在はコンピューティングユニットと呼ばれるポイントで使用量が管理されているようです。
ところで、GPUクラスをプレミアムに設定したとき割り当てられるGPUはA100かV100の2択らしいんですが、V100ってVRAMが16GBのものと32GBのものがあるらしいんですよね。もしV100の16GBモデルが割り当てられてしまった場合、一回ランタイムを切断してガチャをする必要があるかもしれません。
訓練するのに先程前処理した学習データと2.でダウンロードしたモデルが必要ですが、自分はこんな感じでCloud Storage上に置いてそれを取ってくるようにしました。
訓練時にはチェックポイントが一定のstepsごとにcheckpoints
内に保存されていきますが、この状態だとランタイムを切断すると消えてしまうのでちゃんとダウンロードしておきましょう。
Colabはもともと色々なPythonのパッケージがインストールされていますが、一部足りないパッケージがあるので訓練前に!pip install -r requirements_short.txt
でパッケージのインストールをしておきます。
また、これだけだとtorchtext.legacyが存在しないみたいなエラーで怒られたのでpytorch-lightning
をアプデしておくといいです。自分は今回1.8.5を使いました。
あとは訓練を回すのみ。
右のパネルを見れば分かる通り、訓練中はVRAMを23.3GB食ってました。もしかすると、VRAM24GBぴったりのGPU(RTX 3090など)だと絶妙にできないかも……?
今回訓練に使用したのは15秒間の音声データ804個分でしたが、64000stepsくらいまでやって所要時間8時間半くらい。A100使ってなかったら、めちゃくちゃ時間かかってそうです。使ってよかったかも。
A100を使うためにColab Proで付いてくるコンピューティングユニット100と追加で100買ったのですが、115くらい使いました。まあ、A100を買おうとしたら普通に100万円じゃ済みませんから、2200円くらいで簡単にこのレベルのGPUを借りれるのは、非常に便利ですね……。GCEだったらいくらになるんでしょうね。
最近はModalっていうGPUを比較的安く借りられるサービスもあるみたいですね。
使い方がちょっと複雑っぽいですが、こちらでもA100は借りれるみたいなので選択肢としてありかも?
6. 推論
で、やりたかったことはここから。モデルができたのはいいですが、Diff-SVCは声質変換をしてくれるもので、text-to-speechができるモデルではありません。
でもまあ、じゃあVOICEVOXとかCOEIROINKで適当に音声を生成してそれを声質変換にかければそれっぽいのができますよね。
COEIROINKのつくよみちゃんを使って作ったサンプル。(音量の調節をしてないので出力が小さいです)
声質変換する前の音声データ:
変換した音声データ:
音質が荒く聴こえるのは、サンプリングレートが低いせい?
画像のsuper-resolutionみたいに、音声の品質を上げてくれるみたいなソフトウェアがあると嬉しいんだけど、あるのかな。
入力側のアクセントとかを直してあげれば、もっといい感じにできるはず。
ちなみに、推論は普通にRTX 3070でもできます。しかも結構高速。いいですね。
Diff-SVCの本領である歌声とかもやってみたい。うまくできるかなあ。
(もっとサンプル追加できたらする)
その他の似たサービスとか
MicrosoftのVALL-Eが完全にDiff-SVCの上位互換ですが、まあどうせそんなに簡単に一般公開されるはずがないので、今回声質変換モデルを自作してみました。
もっとお手軽な音声合成サービスとしてElevenLabsが公開しているPrime Voice AIというのもあります。英語限定ですが、こちらも面白いです。
まあDiff-SVCも訓練自体は時間がかかるとはいえ、逆に言えばほとんど待つだけで今回くらいの品質を出せるということで、かなり簡単ではあると思います。
簡単になりすぎても、Deepfakeやらなんやらでよくないですが……。
追記
後継っぽい別の手法でやった続編出ました。こちらの方がより簡単です。