「WeSpeaker」で音声ベクトルによる話者識別を試す
発端は以下
GitHubレポジトリ
READMEから抜粋。翻訳はPLaMo翻訳。
WeSpeaker
ロードマップ | ドキュメント | 論文 | 実行環境 | 事前学習済みモデル | Huggingfaceデモ | Modelscopeデモ
WeSpeakerは主に話者埋め込み学習に焦点を当てており、話者認証タスクへの応用が可能です。kaldi形式の事前抽出済み特徴量のオンライン抽出または読み込みをサポートしています。
インストール方法
Pythonパッケージのインストール
pip install git+https://github.com/wenet-e2e/wespeaker.gitコマンドラインでの使用方法(パラメータの詳細は
-hオプションを参照):$ wespeaker --task embedding --audio_file audio.wav --output_file embedding.txt $ wespeaker --task embedding_kaldi --wav_scp wav.scp --output_file /path/to/embedding $ wespeaker --task similarity --audio_file audio.wav --audio_file2 audio2.wav $ wespeaker --task diarization --audio_file audio.wavPythonプログラムでの使用方法:
import wespeaker model = wespeaker.load_model('chinese') embedding = model.extract_embedding('audio.wav') utt_names, embeddings = model.extract_embedding_list('wav.scp') similarity = model.compute_similarity('audio1.wav', 'audio2.wav') diar_result = model.diarize('audio.wav')詳細なコマンドラインおよびPythonプログラムでの使用方法については、Python使用ガイドを参照してください。
🔥 最新情報
- 2025年2月23日:Xi-vector形式のサポートを追加しました #404 を参照してください。
- 2024年9月3日:SimAM_ResNetモデルとVoxBlink2で事前学習済みモデルをサポートしました。事前学習済みモデルについては事前学習済みモデル、優れた性能を実現するVoxCelebレシピについてはVoxCelebレシピ、コマンドラインでの使用方法についてはPython使用ガイドをご覧ください。
- 2024年8月30日:whisper_encoderベースのフロントエンドをサポートし、Whisper-PMFAフレームワークを提案しました。詳細は#356をご覧ください。
- 2024年8月20日:umap次元削減とhdbscanクラスタリングを活用したVoxConverseデータセット向けのダイアライゼーションレシピを更新しました。詳細は#347および#352をご覧ください。
- 2024年8月18日:SSLで事前学習済みモデルをフロントエンドとして使用できるようにしました。WavLMレシピも提供しています。詳細は#344をご覧ください。
- 2024年5月15日:品質を考慮したスコア較正機能を追加しました。詳細は#320をご覧ください。
- 2024年4月25日:gemini-dfresnetモデルのサポートを追加しました。詳細は#291をご覧ください。
- 2024年4月23日:実行時環境におけるMNN推論エンジンをサポートしました。詳細は#310をご覧ください。
- 2024年4月2日:詳細なモデル学習チュートリアルや各種実行環境の紹介などを収録したWespeakerドキュメントを公開しました。
詳細はPython使用ガイドを参照してください。- 2024年3月4日:damo社提供のeres2net-cn-common-200kおよびcampplus-cn-common-200kモデルをサポートしました#281。具体的なPython使用方法については[こちら]をご覧ください。
- 2024年2月5日:ERes2Net#272およびRes2Net#273モデルのサポートを追加しました。
- 2023年11月13日:wespeakerのCLI(コマンドラインインターフェース)使用をサポートしました。詳細なPython使用方法については[こちら]をご覧ください。
- 2023年7月18日:kaldi互換のPLDA(Probabilistic Latent Semantic Analysis)および教師なし適応機能をサポートしました。詳細は#186を参照してください。
- 2023年7月14日:NIST SRE16レシピをサポートしました。詳細は#177をご覧ください。
使用例
- VoxCeleb: VoxCelebデータセットを使用した話者認証レシピ
- 🔥 2024年5月15日更新:VoxCeleb向けスコア較正機能を追加し、性能向上を実現しました!
- 🔥 2023年7月10日更新:VoxCeleb向け自己教師あり学習レシピをサポート!ラベルなしデータ環境において、vox1-O-cleanテストセットで2.627%(ECAPA_TDNN_GLOB_c1024)のEERを達成しました。
- 🔥 2022年10月31日更新:293層バージョンまでの深層r-vector機能をサポート!vox1-O-cleanテストセットで0.447%/0.043のEER/mindcfを達成しました。
- 🔥 2022年7月19日更新:CNCelebレシピと同様の設定を適用し、オープンソースシステムとして最高水準の性能を達成しました。
- LMファインチューニングとAS-Norm適用後のvox1-O-cleanテストセットにおけるEER/minDCFは、ResNet34で0.723%/0.069、ECAPA_TDNN_GLOB_c1024で0.728%/0.099です
- CNCeleb: CnCelebデータセット向け話者認証レシピ
- NIST SRE16: 2016年NIST話者認識評価計画向け話者認証レシピ。類似のレシピはKaldiでも確認できます。
- 🔥 2023年7月14日更新:NIST SRE16向けレシピをサポートしました。PLDA適応後、トライアルデータセットにおいてPooledで6.608%、タガログ語で10.01%、広東語で2.974%のEERを達成しました。
- VoxConverse: VoxConverseデータセットを対象としたダイアリゼーションレシピ
レポジトリのライセンスはApache-2.0。
事前学習済みモデルは以下に記載がある。こちらも翻訳はPLaMo翻訳。
WeSpeakerに搭載されている事前学習済みモデルについて
話者関連タスクに加え、話者埋め込み表現は以下のような話者モデリングを必要とする様々な関連タスクにも活用可能です:
- 音声変換
- テキスト音声合成
- 話者適応型自動音声認識(ASR)
- 特定話者抽出
SV(話者ベクトル)の性能検証や、上記タスク向けの話者埋め込み表現を、話者埋め込み学習モデルの訓練作業なしで取得したいユーザー向けに、当社では2種類の事前学習済みモデルを提供しています。
- チェックポイントモデル(拡張子:.pt):WeSpeakerのPythonコードによって訓練・保存されたモデルで、当社の公開結果を再現できるほか、チェックポイントとして継続して使用することも可能です。
- ランタイムモデル(拡張子:.onnx):
Onnxruntimeを用いてチェックポイントモデルからエクスポートされたランタイムモデルです。モデルのライセンスについて
WeNetに搭載されている事前学習済みモデルは、対応するデータセットのライセンスに準拠しています。
例えば、VoxCeleb用の事前学習済みモデルはCreative Commons Attribution 4.0 International Licenseに準拠しています。これは当該モデルがVoxCelebデータセットのライセンス条件に従っているためです(詳細は https://mm.kaist.ac.kr/datasets/voxceleb/ をご覧ください)。Onnx推論デモ
pytorch形式の事前学習済みモデルを使用する場合は、対応するレシピ内のrun.shスクリプトを直接参照してください。
onnxモデルから話者埋め込みを抽出する場合、以下に簡単な使用例を示します。# onnx形式の事前学習済みモデルをダウンロードし、onnx_pathとして保存します # wav_pathは使用するwavファイルのパスです(サンプリングレート16kHz) python wespeaker/bin/infer_onnx.py --onnx_path $onnx_path --wav_path $wav_path
infer_onnx.pyスクリプトはご自身のアプリケーションに容易に適応可能です。話者ダイアライゼーションの使用例については、以下の例を参照してください:
voxconverseレシピ。モデル一覧
モデル名にLMのサフィックスが付いている場合、これは大規模マージンファインチューニングによってさらに微調整されたモデルであることを示しています。このようなモデルは、3秒以上の長時間音声に対してより優れた性能を発揮する可能性があります。
modelscope
データセット 対応言語 チェックポイント(pt形式) 実行時モデル(onnx形式) VoxCeleb EN ResNet34 / ResNet34_LM ResNet34 / ResNet34_LM VoxCeleb EN ResNet152_LM ResNet152_LM VoxCeleb EN ResNet221_LM ResNet221_LM VoxCeleb EN ResNet293_LM ResNet293_LM VoxCeleb EN CAM++ / CAM++_LM CAM++ / CAM++_LM VoxCeleb EN ECAPA512 / ECAPA512_LM / ECAPA512_DINO ECAPA512 / ECAPA512_LM VoxCeleb EN ECAPA1024 / ECAPA1024_LM ECAPA1024 / ECAPA1024_LM VoxCeleb EN Gemini_DFResnet114_LM Gemini_DFResnet114_LM CNCeleb CN ResNet34 / ResNet34_LM ResNet34 / ResNet34_LM VoxBlink2 Multilingual SimAMResNet34 SimAMResNet34 VoxBlink2 (事前学習済み) + VoxCeleb2 (ファインチューニング) Multilingual SimAMResNet34 SimAMResNet34 VoxBlink2 Multilingual SimAMResNet100 SimAMResNet100 VoxBlink2 (事前学習済み) + VoxCeleb2 (ファインチューニング) Multilingual SimAMResNet100 SimAMResNet100 huggingface
データセット 対応言語 Checkpoint (pt) 実行時モデル (onnx) VoxCeleb EN ResNet34 / ResNet34_LM ResNet34 / ResNet34_LM VoxCeleb EN ResNet152_LM ResNet152_LM VoxCeleb EN ResNet221_LM ResNet221_LM VoxCeleb EN ResNet293_LM ResNet293_LM VoxCeleb EN CAM++ / CAM++_LM CAM++ / CAM++_LM VoxCeleb EN ECAPA512 / ECAPA512_LM ECAPA512 / ECAPA512_LM VoxCeleb EN ECAPA1024 / ECAPA1024_LM ECAPA1024 / ECAPA1024_LM VoxCeleb EN Gemini_DFResnet114_LM Gemini_DFResnet114_LM CNCeleb CN ResNet34 / ResNet34_LM ResNet34 / ResNet34_LM
日本語に限らずよく使われているのは wespeaker-voxceleb-resnet34-LM みたい。
データセットが異なるマルチリンガルモデルもあるんだけど、各データセットのライセンスを見てみる。
VoxCelebデータセットは、研究目的でCreative Commons表示4.0国際ライセンスの下でダウンロード可能です。ただし、動画の著作権は原権利者が保持しています。ライセンスの全文はこちらで確認できます。
本データセットに含まれるすべてのリソースは、研究機関および個人による研究目的で自由に利用できます。ただし、音声/動画の著作権は原権利者が保持しており、商用利用は一切許可されていません。
オープンソースとして提供するリソースおよび実行スクリプトは、保護の観点からCC BY-NC-SA 4.0ライセンスの下で公開しています。詳細なライセンス条件についてはLICENSEファイルをご確認ください。
なるほど、ライセンス的なところと、あとモデルサイズと精度からすると一番小さなwespeaker-voxceleb-resnet34-LMで十分という感じかな。評価は以下が参考になる。
READMEに従って試してみる。最初にMacで試してみたのだけど、いろいろ詰まることが多かったので、Ubuntu-22.04(RTX4090)で。
仮想環境作成
mkdir wespeaker-work && cd $_
uv venv -p 3.12 --seed
パッケージインストール。PyTorchもインストールされるので、--torch-backend=autoをつけたほうが良さそう。
uv pip install git+https://github.com/wenet-e2e/wespeaker.git --torch-backend=auto
(snip)
+ wespeaker==0.0.0 (from git+https://github.com/wenet-e2e/wespeaker.git@67f0f4a8d472e6e2203d7baca38daba818af17f3)
ドキュメントには上記のみしか書いてないが、実際には以下も必要になる(ないとCLIでエラーになる)
uv pip install PyYAML requests
まず、CLI。Usageを見てみる。
uv run wespeaker -h
usage: wespeaker [-h] [-t {embedding,embedding_kaldi,similarity,diarization,diarization_list}] [-l {chinese,english}]
[--campplus] [--eres2net] [--vblinkp] [--vblinkf] [-p PRETRAIN] [--device DEVICE]
[--audio_file AUDIO_FILE] [--audio_file2 AUDIO_FILE2] [--wav_scp WAV_SCP]
[--resample_rate RESAMPLE_RATE] [--vad] [--output_file OUTPUT_FILE]
[--diar_min_duration DIAR_MIN_DURATION] [--diar_window_secs DIAR_WINDOW_SECS]
[--diar_period_secs DIAR_PERIOD_SECS] [--diar_frame_shift DIAR_FRAME_SHIFT]
[--diar_emb_bs DIAR_EMB_BS] [--diar_subseg_cmn DIAR_SUBSEG_CMN]
options:
-h, --help show this help message and exit
-t {embedding,embedding_kaldi,similarity,diarization,diarization_list}, --task {embedding,embedding_kaldi,similarity,diarization,diarization_list}
task type
-l {chinese,english}, --language {chinese,english}
language type
--campplus whether to use the damo/speech_campplus_sv_zh-cn_16k-common model
--eres2net whether to use the damo/speech_eres2net_sv_zh-cn_16k-common model
--vblinkp whether to use the samresnet34 model pretrained on voxblink2
--vblinkf whether to use the samresnet34 model pretrained on voxblink2 andfintuned on voxceleb2
-p PRETRAIN, --pretrain PRETRAIN
model directory
--device DEVICE device type (most commonly cpu or cuda,but also potentially mps, xpu, xla or meta)and optional
device ordinal for the device type.
--audio_file AUDIO_FILE
audio file
--audio_file2 AUDIO_FILE2
audio file2, specifically for similarity task
--wav_scp WAV_SCP path to wav.scp, for extract and saving kaldi-stype embeddings
--resample_rate RESAMPLE_RATE
resampling rate
--vad whether to do VAD or not
--output_file OUTPUT_FILE
output file to save speaker embedding or save diarization result
--diar_min_duration DIAR_MIN_DURATION
VAD min duration
--diar_window_secs DIAR_WINDOW_SECS
the window seconds in embedding extraction
--diar_period_secs DIAR_PERIOD_SECS
the shift seconds in embedding extraction
--diar_frame_shift DIAR_FRAME_SHIFT
frame shift in fbank extraction (ms)
--diar_emb_bs DIAR_EMB_BS
batch size for embedding extraction
--diar_subseg_cmn DIAR_SUBSEG_CMN
do cmn after or before fbank sub-segmentation
READMEのCLIのサンプルを順に試してみる。サンプルは過去に自分が主催した勉強会の冒頭1分程度の音声(voice_lunch_jp_1min.wav、実際には43秒)を使った。なお、発話者は自分だけ。
音声ベクトルの作成
uv run wespeaker \
--task embedding \
--audio_file voice_lunch_jp_1min.wav \
--output_file embedding.txt
初回はモデルがダウンロードされる。どうやらデフォルトは 中国語向けの cnceleb_resnet34 になるみたい。
Downloading https://dataset-hub.oss-cn-hangzhou.aliyuncs.com/public-unzip-dataset/wenet/wespeaker_pretrained_models/master/cnceleb_resnet34.tar.gz?Expires=1764275664&OSSAccessKeyId=LTAI5tAoCEDFQFyV5h8unjt8&Signature=Z79oZjXQW2QFdEAHtVVz96gKzAo%3D&response-content-disposition=attachment%3B to /home/kun432/.wespeaker/chinese
cnceleb_resnet34.tar.gz: 100%|█████████████████████████████████████████████████████| 31.1M/31.1M [00:04<00:00, 6.71MB/s]
エラー。
ImportError: TorchCodec is required for load_with_torchcodec. Please install torchcodec to use this function.
torchcodecも必要みたい。
uv pip install torchcodec
(snip)
+ torchcodec==0.8.1
再度実行
uv run wespeaker \
--task embedding \
--audio_file voice_lunch_jp_1min.wav \
--output_file embedding.txt
今度は成功した模様。
Succeed, see embedding.txt
embedding.txtはこんな感じ。
9.884694963693618774e-02
-6.712152808904647827e-02
1.572865545749664307e-01
2.066522091627120972e-01
-3.340280950069427490e-01
(snip)
-1.994613707065582275e-01
-2.906784117221832275e-01
-1.107062846422195435e-01
-5.282661318778991699e-02
-3.054174780845642090e-01
256次元ってことかな?
wc -l embedding.txt
256 embedding.txt
日本語でもよく使われている wespeaker-voxceleb-resnet34-LM をダウンロード。
git lfs install
git clone https://huggingface.co/Wespeaker/wespeaker-voxceleb-resnet34-LM
ダウンロードした事前学習モデルを指定して再度実行。
uv run wespeaker \
--pretrain ./wespeaker-voxceleb-resnet34-LM \
--task embedding \
--audio_file voice_lunch_jp_1min.wav \
--output_file embedding2.txt
エラー
File "/work/wespeaker-work/.venv/lib/python3.12/site-packages/wespeaker/cli/speaker.py", line 343, in main
model = load_model(model_dir=args.pretrain)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
TypeError: load_model() got an unexpected keyword argument 'model_dir'
ここか。
引数名が変わったのかも。エラーの該当箇所を以下のように書き換え。
model = load_model(model_name_or_path=args.pretrain)
再実行するも今度は別のエラー。
raise FileNotFoundError(f"{file} not found in {model_dir}")
FileNotFoundError: avg_model.pt not found in ./wespeaker-voxceleb-resnet34-LM
ダウンロードしたモデルパスを見てみる。
tree wespeaker-voxceleb-resnet34-LM/
wespeaker-voxceleb-resnet34-LM/
├── README.md
├── avg_model
├── config.yaml
└── voxceleb_resnet34_LM.onnx
0 directories, 4 files
んー、ファイル名だけ???ONNXの方もあるんだけど、CLI見てもそれっぽいものがない、どうすれば使えるのかな?
とりあえずリネームしてみる。
cp wespeaker-voxceleb-resnet34-LM/avg_model wespeaker-voxceleb-resnet34-LM/av
g_model.pt
再度実行したらうまくいった。
Succeed, see embedding2.txt
生成されたembeddingはこんな感じ。
-1.454869508743286133e-01
-1.880786567926406860e-02
2.014929242432117462e-02
2.714627981185913086e-01
8.721305429935455322e-02
(snip)
1.460620611906051636e-01
1.842129677534103394e-01
7.246416062116622925e-03
1.637877374887466431e-01
2.479757070541381836e-01
wc -l embedding2.txt
256 embedding2.txt
あと、embedding_kaldi ってのがあるけど、これはKaldiを使った音声ベクトル生成ってことかな?wav.scpってのはあんまり良くわかってないけど、音声IDと音声ファイルを紐付けたものになるらしい。m3uみたいなものかしら。とりあえずこれはパスで。
wespeaker --task embedding_kaldi --wav_scp wav.scp --output_file /path/to/embedding
音声の類似度
--task similarityで音声の類似度を算出する。上で使ったサンプル音声に加えて、以下を用意した。
-
my_sample.wav: 自分の声の音声データ、つまり上のサンプル音声と同じ声。7秒程度。 -
other_sample.wav: 何かしらのTTSで生成した音声データ、女性の声、つまり上のサンプル音声とは別の声。5秒程度。 -
voice_lunch_jp_15sec.wav: 上のサンプル音声の15秒バージョン、つまり全く同じ音声。
それぞれを上で使ったサンプル音声と比較してみる。
uv run wespeaker \
--pretrain ./wespeaker-voxceleb-resnet34-LM \
--task similarity \
--audio_file voice_lunch_jp_1min.wav \
--audio_file2 my_sample.wav
0.8032963275909424
uv run wespeaker \
--pretrain ./wespeaker-voxceleb-resnet34-LM \
--task similarity \
--audio_file voice_lunch_jp_1min.wav \
--audio_file2 other_sample.wav
0.532842256128788
uv run wespeaker \
--pretrain ./wespeaker-voxceleb-resnet34-LM \
--task similarity \
--audio_file voice_lunch_jp_1min.wav \
--audio_file2 voice_lunch_jp_15sec.wav
0.9200428426265717
まあそれっぽい感じにはなってるかな。
話者ダイアライぜーション
--task dialization で話者ダイアライぜーションができる。
uv run wespeaker \
--pretrain ./wespeaker-voxceleb-resnet34-LM \
--task diarization \
--audio_file voice_lunch_jp_1min.wav
0.900 6.200 0
6.900 7.900 0
8.100 9.300 0
9.600 10.900 0
11.500 12.500 0
13.900 23.200 0
23.500 26.100 0
26.500 36.600 0
36.700 39.000 0
40.100 40.700 0
40.900 42.800 0
開始秒・終了秒・話者IDみたいな感じなのだろうか?
複数人の音声会話でも試してみる。以前試したSonioxというASRサービスのデモレポジトリに、コーヒーショップでの店員(女性)と客(男性)の会話のデータ(coffee_shop.mp3)があったのでそれを使わせてもらう。
15秒程度で以下のような会話になっている。(出力はSonioxでのもの)
Speaker 1:
[en] What is your best seller here?
Speaker 2:
[en] Our best seller here is cold brew iced coffee and lattes.
Speaker 1:
[en] Okay. And on a day like today, where it's snowing quite a bit, do a lot of people still order iced coffee?
Speaker 2:
[en] Here in Maine, yes.
Speaker 1:
[en] Really?
Speaker 2:
[en] Yes.
なお、wespeakerはWAVファイルのみとなるため、事前にWAVに変換しておく必要がある。自分はffmpegを使用した。
ffmpeg -i coffee_shop.mp3 coffee_shop.wav
uv run wespeaker \
--pretrain ./wespeaker-voxceleb-resnet34-LM \
--task diarization \
--audio_file coffee_shop.wav
0.600 2.000 0
2.200 5.400 0
5.600 10.900 0
11.100 16.070 0
んー、話者が一人になってしまう・・・
オプションなどを見ていると、どうやらVAD(SileroVAD)で発話区間を分割して判定ができるみたい?以下のようにパラメータを設定してみた。
uv run wespeaker \
--pretrain ./wespeaker-voxceleb-resnet34-LM \
--task diarization \
--audio_file coffee_shop.wav \
--vad \
--diar_min_duration 0.05 \
--diar_window_secs 0.5 \
--diar_period_secs 0.25
それっぽくなってるね。
0.600 1.225 0
1.225 2.000 1
2.200 5.400 1
5.600 8.225 1
8.225 10.475 0
10.475 10.900 1
11.100 12.225 0
12.225 12.475 1
12.475 12.975 0
12.975 16.070 1
VADまわりのオプションはこんな感じ
Pythonから使う
Pythonから使う。
音声のベクトル化
import wespeaker
model = wespeaker.load_model("./wespeaker-voxceleb-resnet34-LM")
model.set_device('cuda:0')
embedding = model.extract_embedding('voice_lunch_jp_15sec.wav')
print(type(embedding))
print(embedding.shape)
print(embedding)
<class 'torch.Tensor'>
torch.Size([256])
tensor([-0.0147, -0.0353, -0.2119, 0.2899, 0.0600, -0.0959, -0.3547, -0.3344,
-0.1263, 0.1023, 0.2098, -0.1215, 0.2277, -0.0788, -0.0625, -0.0447,
0.2672, -0.0007, 0.1421, -0.0700, -0.1575, -0.0538, -0.1317, 0.0093,
(snip)
0.1442, -0.2110, -0.2013, -0.1815, -0.0191, 0.5470, 0.2977, -0.0162,
-0.0375, -0.3550, 0.0343, 0.1208, -0.1204, -0.0154, 0.1941, -0.2209,
-0.0923, -0.0446, 0.1504, 0.1633, 0.1414, -0.0021, 0.0977, 0.2701])
類似度
import wespeaker
model = wespeaker.load_model("./wespeaker-voxceleb-resnet34-LM")
model.set_device('cuda:0')
similarity1 = model.compute_similarity(
'voice_lunch_jp_15sec.wav',
'my_sample.wav'
)
print(similarity1)
similarity2 = model.compute_similarity(
'voice_lunch_jp_15sec.wav',
'other_sample.wav'
)
print(similarity2)
0.8291692435741425
0.5287035647779703
話者ダイアライぜーション
import wespeaker
model = wespeaker.load_model("./wespeaker-voxceleb-resnet34-LM")
model.set_device('cuda:0')
diar_result = model.diarize('coffee_shop.wav')
print(diar_result)
[('unk', 0.6, 2.0, 0), ('unk', 2.2, 5.4, 0), ('unk', 5.6, 10.9, 0), ('unk', 11.1, 16.07, 0)]
VADを有効にしてみる。
import wespeaker
model = wespeaker.load_model("./wespeaker-voxceleb-resnet34-LM")
model.set_device('cuda:0')
# VADを有効化
model.set_vad(True)
#VADのパラメータをセット
model.set_diarization_params(
min_duration=0.05,
window_secs=0.5,
period_secs=0.25,
)
diar_result = model.diarize('coffee_shop.wav')
print(diar_result)
[('unk', 0.6, 2.0, 0), ('unk', 2.2, 5.4, 0), ('unk', 5.6, 6.225, 1), ('unk', 6.225, 10.9, 0), ('unk', 11.1, 13.725, 0), ('unk', 13.725, 13.975, 1), ('unk', 13.975, 16.07, 0)]
ドキュメントがほとんどないのだけども、基本的なインタフェース部分は wespeaker/cli/speaker.py をみればだいたい把握できそう
wespeaker-voxceleb-resnet34-LM は pyannotate.audio 経由で使うこともできる。