話者分離と音声認識 (定番のpyannote.audioでなくNeMoのdiarization modelを利用)+日本語化

ネット上を眺めると、python環境での話者分離には pyannote.audio を使うのが通例になっている。
ただ、pyannote.audioの利用にはhuggingface発行のトークンを使う必要がある。オフラインで利用できなくもないが、その準備が面倒だ。
これ以外の選択肢はないか? .... ある

NeMoのdiarization modelで話者分離したあとにwhisperを適用するものらしい。

whisper-diarizationのコードは、6c9047dd7334c48acde62042890fd357117a9f55 (2025/02/05現在)。
cuDNN9のシンボルがない旨のエラーで終わる。
以下に従う。ctranslate2==4.5.0 が cuDNN 9.2に密結合しているので、ダウングレードする。
Here the culprit is ctranslate2. The library was just updated to version 4.5.0, which uses
cuDNN 9.2. Downgrading ctranslate to version 4.4.0 is enough to fix the problem,
# Ubuntu22.04/WSL2 + CUDA12
sudo apt update && sudo apt install cython3
sudo apt update && sudo apt install ffmpeg
# パッケージをインストール
pip install -c constraints.txt -r requirements.txt
# ctranslate2 を 4.5.0 より以前にダウングレード
pip install ctranslate2==4.4.0
# サンプル音声を入手
wget https://huggingface.co/kotoba-tech/kotoba-whisper-v2.2/resolve/main/sample_audio/sample_diarization_japanese.mp3
# 話者分離
python diarize.py -a sample_diarization_japanese.mp3
動いた。英語のモデルで、英語前提らしい。英語に翻訳されている。
$ more sample_diarization_japanese.txt
Speaker 0: So this is almost like a little jib on the kangkaku taking a day job high skill. No more email. Oh, cool. I know kiyo. She don't know. You must cook in real life. Okay, they were high school.
Speaker 1: I think you must go to a place on a machine. Oh, I feel is the good news. Oh, you see, not doing at the weather for your PR section.
Speaker 2: That's your name. Mizzo, Malaysia. Cara, kawanak to another notice.
$ more sample_diarization_japanese.srt
1
00:00:00,220 --> 00:00:04,956
Speaker 0: So this is almost like a little jib on the kangkaku taking a day job high skill.
2
00:00:05,082 --> 00:00:06,111
Speaker 0: No more email.
3
00:00:06,174 --> 00:00:06,909
Speaker 0: Oh, cool.
4
00:00:07,119 --> 00:00:07,854
Speaker 0: I know kiyo.
5
00:00:08,379 --> 00:00:09,261
Speaker 0: She don't know.
6
00:00:09,303 --> 00:00:11,634
Speaker 0: You must cook in real life.
7
00:00:12,411 --> 00:00:13,482
Speaker 0: Okay, they were high school.
8
00:00:13,545 --> 00:00:16,422
Speaker 1: I think you must go to a place on a machine.
9
00:00:16,884 --> 00:00:18,144
Speaker 1: Oh, I feel is the good news.
10
00:00:18,186 --> 00:00:21,840
Speaker 1: Oh, you see, not doing at the weather for your PR section.
11
00:00:21,882 --> 00:00:23,436
Speaker 2: That's your name.
12
00:00:23,478 --> 00:00:24,276
Speaker 2: Mizzo, Malaysia.
13
00:00:24,381 --> 00:00:27,909
Speaker 2: Cara, kawanak to another notice.

日本語で
$ python diarize.py --whisper-model large --language ja -a sample_diarization_japanese.mp3
$ more sample_diarization_japanese.txt
Speaker 1: そ う で す ね こ れ も 先 ほ ど ず っ と 言 っ て い る 自 分 の 感 覚 的 に は 大 丈 夫 で す け れ ど も も う 今 は 屋 外 の 気 温 昼 も 夜 も 上 が っ て ま す の で 空 気 の 入 れ 替 え だ け で は か え っ て 人 が
上 が っ
Speaker 2: て き ま す や っ ぱ り 愚 直 に や っ ぱ り そ の 街 の 良 さ を ア ピ ー ル し て い く っ て い う そ う い う 姿 勢 が 基 本 に あ っ た 上 で の こ う い う P R 作 戦
Speaker 0: だ と 思 う ん で す よ ね 水 を マ レ ー シ ア か ら 買 わ な く て は な ら な い の で す
$ more sample_diarization_japanese.srt
1
00:00:00,220 --> 00:00:13,671
Speaker 1: そ う で す ね こ れ も 先 ほ ど ず っ と 言 っ て い る 自 分 の 感 覚 的 に は 大 丈 夫 で す け れ ど も も う 今 は 屋 外 の 気 温 昼 も 夜 も 上 が っ て ま す の で 空 気 の 入 れ 替 え だ け で は か え っ て 人 が
上 が っ
2
00:00:13,713 --> 00:00:21,840
Speaker 2: て き ま す や っ ぱ り 愚 直 に や っ ぱ り そ の 街 の 良 さ を ア ピ ー ル し て い く っ て い う そ う い う 姿 勢 が 基 本 に あ っ た 上 で の こ う い う P R 作 戦
3
00:00:21,882 --> 00:00:27,909
Speaker 0: だ と 思 う ん で す よ ね 水 を マ レ ー シ ア か ら 買 わ な く て は な ら な い の で す
タイムスロットのようなものがあるのか、文末が、次の話者にまたがっている印象。
WARNING:root:Punctuation restoration is not available for ja language. Using the original punctuation.
実行中、上記のメッセージが出力されているので、日本語のpunctuationは上手ではないのかもしれない。

punctuationを別モデルにさせればよいのだろうな。

(別スクラップから転記)2025-02-13 17:11
punctuationモデルが日本語対応していないので、話者ごとの発話末尾の切り出しがうまくない。
使われているpunctuationモデルを日本語対応させるか、日本語対応のpunctuationモデルで差し替えるか。後者で考えてみる。
↑これをつかって、インタフェースを合わせこんでやればよいだろうか。

(別スクラップから転記)2025-06-10 00:17
差し替えてみた。しかし、よく見ると差し替えても意味がない。
日本語の文区切りは入るようになったが、話者分離の区切りは変わらない。
よって、日本語文の途中で話者が切り替わるように判断されてしまう。
これは現状のdiarizationモデルの限界なのだろう。
Known Limitationsの一つ目がそれか。
Overlapping speakers are yet to be addressed, a possible approach would be to separate the audio file and isolate only one speaker, then feed it into the pipeline but this will need much more computation
Speaker 1: そ う で す ね。 こ れ も 先 ほ ど ず っ と 言 っ て い る 自 分 の 感 覚 的 に は 大 丈 夫 で す。 け れ ど も 今 は 屋 外 の 気 温 昼 も 夜 も 上 が っ て ま す の で 空 気 の 入 れ 替 え だ け で は か え っ て 人 が 上 が っ
Speaker 2: て き ま す。 や っ ぱ り 愚 直 に や っ ぱ り そ の 街 の 良 さ を ア ピ ー ル し て い く っ て い う そ う い う 姿 勢 が 基 本 に あ っ た 上 で の こ
Speaker 1: う い う P R 作 戦
Speaker 0: だ と 思 う ん で す よ ね。 水 を マ レ ー シ ア か ら 買 わ な く て は な ら な い の で す。
1
00:00:00,220 --> 00:00:13,671
Speaker 1: そ う で す ね。 こ れ も 先 ほ ど ず っ と 言 っ て い る 自 分 の 感 覚 的 に は 大 丈 夫 で す。 け れ ど も 今 は 屋 外 の 気 温 昼 も 夜 も 上 が っ て ま す の で 空 気 の 入 れ 替 え だ け で は か え っ て 人 が 上 が っ
2
00:00:13,713 --> 00:00:20,958
Speaker 2: て き ま す。 や っ ぱ り 愚 直 に や っ ぱ り そ の 街 の 良 さ を ア ピ ー ル し て い く っ て い う そ う い う 姿 勢 が 基 本 に あ っ た 上 で の こ
3
00:00:21,000 --> 00:00:21,840
Speaker 1: う い う P R 作 戦
4
00:00:21,882 --> 00:00:27,909
Speaker 0: だ と 思 う ん で す よ ね。 水 を マ レ ー シ ア か ら 買 わ な く て は な ら な い の で す。

(別スクラップから転記)2025-06-11 21:13
これは現状のdiarizationモデルの限界なのだろう。
まちがい。punctuationの結果で アライメントを取り直させる必要があった。その際の文末判断や、処理対象の長さ設定を見直す必要があった。
if info.language in ["ja"]: # 日本語は1語=1文字で出力されるので、1文あたりの最大語数を多めにとる
helpers.sentence_ending_punctuations = [".","?","!","。","?","!"]
wsm = get_realigned_ws_mapping_with_punctuation(wsm,max_words_in_sentence=1500)
else:
wsm = get_realigned_ws_mapping_with_punctuation(wsm)
ssm = get_sentences_speaker_mapping(wsm, speaker_ts)
結果は期待通り。
1
00:00:00,220 --> 00:00:14,175
Speaker 1: そ う で す ね。 こ れ も 先 ほ ど が ず っ と 言 っ て い る 自 分 の 感 覚 的 に は 大 丈 夫 で す け れ ど も も う 今 は 屋 外 の 気 温 昼 も 夜 も 上 が っ て ま す の で 空 気 の 入 れ 替 え だ け で は か え っ て 人 が 上 が っ て き ま す。
2
00:00:14,217 --> 00:00:22,680
Speaker 2: や っ ぱ り 愚 直 に や っ ぱ り そ の 街 の 良 さ を ア ピ ー ル し て い く っ て い う そ う い う 姿 勢 が 基 本 に あ っ た 上 で の こ う い う P R 作 戦 だ と 思 う ん で す よ ね。
3
00:00:23,394 --> 00:00:27,909
Speaker 0: 水 を マ レ ー シ ア か ら 買 わ な く て は な ら な い の で す。
コードはgithubにforkして。