В модуле Python ошибка list index out of range то возникает, то нет
Изучаю возможности библиотеки resemblyzer для распознавания спикеров. Сравниваю файлы из папок spk1, spk2 и т.д., в каждой из которых лежат минимум 2 записи одного спикера.
После предобработки звука строю эмбединги двух файлов в каждой папке. И если одна запись каждой директории (переменная embeds_a) в свое представление отображается нормально, то с другой не ладится - получаю ошибку
IndexError: list index out of range
Эмбединги двух записей должны получаться вследствие кода:
embeds_a = np.array([encoder.embed_utterance(wavs[0]) for wavs in speaker_wavs.values()])
embeds_b = np.array([encoder.embed_utterance(wavs[1]) for wavs in speaker_wavs.values()])
Проблема выходит на второй строчке с переменной ambeds_b. Здесь speaker_wavs - это словарь. В нем ключи - именования папок (спикеров) spk1, spk2 и т.д., а значения - каждая запись их голоса, разложенная на массивы np.array:
{'spk10': [array([ 0.00150004, 0.00187945, 0.00227684, ..., -0.0005368 ,
-0.00018098, -0.00036559], dtype=float32),
array([-0.00133576, -0.00131788, -0.00158764, ..., 0.0017464 ,
0.00235882, 0.00250746], dtype=float32)],...}
encoder - это объект класса VoiceEncoder, к которому, в том числе, применим метод .embed_utterance() . Под "капотом" метод имеет следующий код:
def embed_utterance(self, wav: np.ndarray, return_partials=False, rate=1.3, min_coverage=0.75):
"""
Вычисляет эмбединг для одного высказывания.
"""
# вычисляем, где можно разделить высказывание на части и дополнить форму сигнала нулями,
# если частичные высказывания охватывают больший диапазон.
wav_slices, mel_slices = self.compute_partial_slices(len(wav), rate, min_coverage)
max_wave_length = wav_slices[-1].stop
if max_wave_length >= len(wav):
wav = np.pad(wav, (0, max_wave_length - len(wav)), "constant")
# Разделяем высказывание на части и передаем их через модель
mel = audio.wav_to_mel_spectrogram(wav)
mels = np.array([mel[s] for s in mel_slices])
with torch.no_grad():
mels = torch.from_numpy(mels).to(self.device)
partial_embeds = self(mels).cpu().numpy()
# Получаем эмбединг высказывания из частичных эмбедингов
raw_embed = np.mean(partial_embeds, axis=0)
embed = raw_embed / np.linalg.norm(raw_embed, 2)
if return_partials:
return embed, partial_embeds, wav_slices
return embed