Transformers documentation
MMS
Эта модель была опубликована в HF papers 22 мая 2023 года и добавлена в Hugging Face Transformers 20 июня 2023 года.
MMS
Обзор
Модель MMS была предложена в статье Scaling Speech Technology to 1,000+ Languages авторами Vineel Pratap, Andros Tjandra, Bowen Shi, Paden Tomasello, Arun Babu, Sayani Kundu, Ali Elkahky, Zhaoheng Ni, Apoorv Vyas, Maryam Fazel-Zarandi, Alexei Baevski, Yossi Adi, Xiaohui Zhang, Wei-Ning Hsu, Alexis Conneau, Michael Auli
Аннотация из статьи следующая:
Расширение языкового охвата речевых технологий способно улучшить доступ к информации для значительно большего числа людей. Однако современные речевые технологии поддерживают лишь около ста языков, что составляет малую долю от более чем 7 000 языков, на которых говорят в мире. Проект Massively Multilingual Speech (MMS) увеличивает количество поддерживаемых языков в 10–40 раз в зависимости от задачи. Ключевыми элементами являются новый датасет, основанный на чтении общедоступных религиозных текстов, и эффективное использование самообучения (self-supervised learning). Мы создали предобученные модели wav2vec 2.0, охватывающие 1 406 языков, одну мультиязычную модель автоматического распознавания речи для 1 107 языков, модели синтеза речи для того же числа языков, а также модель идентификации языка для 4 017 языков. Эксперименты показывают, что наша мультиязычная модель распознавания речи более чем вдвое снижает коэффициент ошибок на слово (WER) по сравнению с Whisper на 54 языках бенчмарка FLEURS, при этом обучаясь на небольшой доле размеченных данных.
Ниже перечислены различные модели, открытые в рамках проекта MMS. Модели и код изначально были опубликованы здесь. Мы добавили их в фреймворк transformers, что упрощает их использование.
Автоматическое распознавание речи (ASR)
Чекпоинты модели ASR можно найти здесь: mms-1b-fl102, mms-1b-l1107, mms-1b-all. Для наилучшей точности используйте модель mms-1b-all.
Советы:
- Все модели ASR принимают массив float, соответствующий исходной волне речевого сигнала. Исходная волна должна быть предварительно обработана с помощью Wav2Vec2FeatureExtractor.
- Модели обучались с использованием классификации временных связей (CTC), поэтому выход модели необходимо декодировать с помощью Wav2Vec2CTCTokenizer.
- Вы можете загрузить веса адаптеров для разных языков с помощью load_adapter(). Адаптеры для языков содержат всего около 2 миллионов параметров, поэтому их можно эффективно загружать по мере необходимости.
Загрузка
По умолчанию MMS загружает веса адаптера для английского языка. Если вы хотите загрузить веса адаптера для другого языка,
убедитесь, что вы также указали target_lang=<your-chosen-target-lang> и "ignore_mismatched_sizes=True.
Ключевое слово ignore_mismatched_sizes=True необходимо передать, чтобы разрешить изменение размера головы языковой модели в соответствии
со словарём указанного языка.
Аналогично, процессор должен быть загружен с тем же целевым языком
from transformers import AutoProcessor, Wav2Vec2ForCTC
model_id = "facebook/mms-1b-all"
target_lang = "fra"
processor = AutoProcessor.from_pretrained(model_id, target_lang=target_lang)
model = Wav2Vec2ForCTC.from_pretrained(model_id, target_lang=target_lang, ignore_mismatched_sizes=True, device_map="auto")Предупреждение такого вида можно смело игнорировать:
Some weights of Wav2Vec2ForCTC were not initialized from the model checkpoint at facebook/mms-1b-all and are newly initialized because the shapes did not match: - lm_head.bias: found shape torch.Size([154]) in the checkpoint and torch.Size([314]) in the model instantiated - lm_head.weight: found shape torch.Size([154, 1280]) in the checkpoint and torch.Size([314, 1280]) in the model instantiated You should probably TRAIN this model on a down-stream task to be able to use it for predictions and inference.
Если вы хотите использовать конвейер ASR, вы можете загрузить выбранный целевой язык следующим образом:
from transformers import pipeline
model_id = "facebook/mms-1b-all"
target_lang = "fra"
pipe = pipeline(model=model_id, model_kwargs={"target_lang": "fra", "ignore_mismatched_sizes": True})Вывод
Далее рассмотрим, как запустить MMS в режиме инференса и изменить адаптерные слои после вызова ~PretrainedModel.from_pretrained. Сначала мы загружаем аудиоданные на разных языках с помощью Datasets.
from datasets import Audio, load_dataset
# English
stream_data = load_dataset("mozilla-foundation/common_voice_13_0", "en", split="test", streaming=True)
stream_data = stream_data.cast_column("audio", Audio(sampling_rate=16000))
en_sample = next(iter(stream_data))["audio"]["array"]
# French
stream_data = load_dataset("mozilla-foundation/common_voice_13_0", "fr", split="test", streaming=True)
stream_data = stream_data.cast_column("audio", Audio(sampling_rate=16000))
fr_sample = next(iter(stream_data))["audio"]["array"]Далее мы загружаем модель и процессор
from transformers import AutoProcessor, Wav2Vec2ForCTC
model_id = "facebook/mms-1b-all"
processor = AutoProcessor.from_pretrained(model_id)
model = Wav2Vec2ForCTC.from_pretrained(model_id, device_map="auto")Теперь мы обрабатываем аудиоданные, передаём обработанные аудиоданные в модель и транскрибируем её вывод, как мы обычно делаем для Wav2Vec2ForCTC.
inputs = processor(en_sample, sampling_rate=16_000, return_tensors="pt").to(model.device)
with torch.no_grad():
outputs = model(**inputs).logits
ids = torch.argmax(outputs, dim=-1)[0]
transcription = processor.decode(ids)
# 'joe keton disapproved of films and buster also had reservations about the media'Теперь мы можем удерживать одну и ту же модель в памяти и просто переключать языковые адаптеры, вызывая удобную функцию load_adapter() для модели и set_target_lang() для токенизатора.
В качестве входного параметра мы передаём целевой язык — "fra" для французского.
processor.tokenizer.set_target_lang("fra")
model.load_adapter("fra")
inputs = processor(fr_sample, sampling_rate=16_000, return_tensors="pt").to(model.device)
with torch.no_grad():
outputs = model(**inputs).logits
ids = torch.argmax(outputs, dim=-1)[0]
transcription = processor.decode(ids)
# "ce dernier est volé tout au long de l'histoire romaine"Тем же самым способом язык можно переключить на любой другой поддерживаемый язык. См.
processor.tokenizer.vocab.keys()
чтобы увидеть все поддерживаемые языки.
Чтобы дополнительно повысить производительность моделей ASR, можно использовать декодирование с языковой моделью. Подробности см. в документации здесь.
Синтез речи (TTS)
MMS-TTS использует ту же архитектуру модели, что и VITS, которая была добавлена в 🤗 Transformers в версии v4.33. MMS обучает отдельную контрольную точку модели для каждого из более чем 1100 языков в проекте. Все доступные контрольные точки можно найти на Hugging Face Hub: facebook/mms-tts, а документация по инференсу — в разделе VITS.
Вывод
Чтобы использовать модель MMS, сначала обновите библиотеку Transformers до последней версии:
pip install --upgrade transformers accelerate
Поскольку flow-based модель в VITS недетерминирована, хорошей практикой является установка seed для обеспечения воспроизводимости результатов.
- Для языков, использующих латиницу, таких как английский или французский, токенизатор можно использовать напрямую для предварительной обработки текстовых входных данных. В следующем примере кода выполняется прямой проход с использованием английской контрольной точки MMS-TTS:
import torch
from transformers import VitsModel, VitsTokenizer, set_seed
tokenizer = VitsTokenizer.from_pretrained("facebook/mms-tts-eng")
model = VitsModel.from_pretrained("facebook/mms-tts-eng", device_map="auto")
inputs = tokenizer(text="Hello - my dog is cute", return_tensors="pt").to(model.device)
set_seed(555) # make deterministic
with torch.no_grad():
outputs = model(**inputs)
waveform = outputs.waveform[0]Полученную звуковую волну можно сохранить в файл .wav:
import scipy
scipy.io.wavfile.write("synthesized_speech.wav", rate=model.config.sampling_rate, data=waveform)Или отображается в Jupyter Notebook / Google Colab:
from IPython.display import Audio
Audio(waveform, rate=model.config.sampling_rate)Для некоторых языков, использующих нелатиницу, таких как арабский, мандаринский или хинди, для предварительной обработки текстовых входных данных в латиницу требуется perl-пакет uroman.
Вы можете проверить, требуется ли вам пакет uroman для вашего языка, обратившись к атрибуту is_uroman предобученного tokenizer:
from transformers import VitsTokenizer
tokenizer = VitsTokenizer.from_pretrained("facebook/mms-tts-eng")
print(tokenizer.is_uroman)При необходимости пакет uroman следует применять к текстовым входным данным до их передачи в VitsTokenizer, поскольку в настоящее время токенизатор не поддерживает выполнение предобработки самостоятельно.
Для этого сначала клонируйте репозиторий uroman на локальную машину и задайте переменной bash UROMAN локальный путь:
git clone https://github.com/isi-nlp/uroman.git
cd uroman
export UROMAN=$(pwd)Затем вы можете выполнить предобработку текстового входа с помощью следующего фрагмента кода. Вы можете использовать bash-переменную UROMAN для указания на репозиторий uroman или передать каталог uroman в качестве аргумента функции uromanize:
import os
import subprocess
import torch
from transformers import VitsModel, VitsTokenizer, set_seed
tokenizer = VitsTokenizer.from_pretrained("facebook/mms-tts-kor")
model = VitsModel.from_pretrained("facebook/mms-tts-kor", device_map="auto")
def uromanize(input_string, uroman_path):
"""Convert non-Roman strings to Roman using the `uroman` perl package."""
script_path = os.path.join(uroman_path, "bin", "uroman.pl")
command = ["perl", script_path]
process = subprocess.Popen(command, stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.PIPE)
# Execute the perl command
stdout, stderr = process.communicate(input=input_string.encode())
if process.returncode != 0:
raise ValueError(f"Error {process.returncode}: {stderr.decode()}")
# Return the output as a string and skip the new-line character at the end
return stdout.decode()[:-1]
text = "이봐 무슨 일이야"
uromanized_text = uromanize(text, uroman_path=os.environ["UROMAN"])
inputs = tokenizer(text=uromanized_text, return_tensors="pt").to(model.device)
set_seed(555) # make deterministic
with torch.no_grad():
outputs = model(inputs["input_ids"])
waveform = outputs.waveform[0]Советы:
- Чекпоинты MMS-TTS обучены на тексте в нижнем регистре без пунктуации. По умолчанию
VitsTokenizerнормализует входные данные, удаляя регистр и знаки препинания, чтобы избежать передачи модели символов, отсутствующих в словаре. Таким образом, модель не зависит от регистра и пунктуации, поэтому их следует избегать в текстовом промпте. Нормализацию можно отключить, установивnormalize=Falseпри вызове токенизатора, однако это приведёт к непредсказуемому поведению и не рекомендуется. - Скорость речи можно изменить, установив атрибут
model.speaking_rateв нужное значение. Аналогично, случайность шума контролируется параметромmodel.noise_scale:
import torch
from transformers import VitsModel, VitsTokenizer, set_seed
tokenizer = VitsTokenizer.from_pretrained("facebook/mms-tts-eng")
model = VitsModel.from_pretrained("facebook/mms-tts-eng", device_map="auto")
inputs = tokenizer(text="Hello - my dog is cute", return_tensors="pt").to(model.device)
# make deterministic
set_seed(555)
# make speech faster and more noisy
model.speaking_rate = 1.5
model.noise_scale = 0.8
with torch.no_grad():
outputs = model(**inputs)Определение языка (LID)
Доступны различные модели LID в зависимости от количества распознаваемых языков — 126, 256, 512, 1024, 2048, 4017.
Вывод
Сначала мы устанавливаем transformers и несколько других библиотек
pip install torch accelerate datasets[audio] pip install --upgrade transformers
Далее мы загружаем несколько аудиопримеров с помощью datasets. Убедитесь, что частота дискретизации аудиоданных составляет 16000 Гц.
from datasets import Audio, load_dataset
# English
stream_data = load_dataset("mozilla-foundation/common_voice_13_0", "en", split="test", streaming=True)
stream_data = stream_data.cast_column("audio", Audio(sampling_rate=16000))
en_sample = next(iter(stream_data))["audio"]["array"]
# Arabic
stream_data = load_dataset("mozilla-foundation/common_voice_13_0", "ar", split="test", streaming=True)
stream_data = stream_data.cast_column("audio", Audio(sampling_rate=16000))
ar_sample = next(iter(stream_data))["audio"]["array"]Далее мы загружаем модель и процессор
from transformers import AutoFeatureExtractor, Wav2Vec2ForSequenceClassification
model_id = "facebook/mms-lid-126"
processor = AutoFeatureExtractor.from_pretrained(model_id)
model = Wav2Vec2ForSequenceClassification.from_pretrained(model_id, device_map="auto")Теперь мы обрабатываем аудиоданные и передаем их в модель для классификации по языку, как мы обычно делаем для моделей классификации аудио Wav2Vec2, таких как ehcalabres/wav2vec2-lg-xlsr-en-speech-emotion-recognition
# English
inputs = processor(en_sample, sampling_rate=16_000, return_tensors="pt").to(model.device)
with torch.no_grad():
outputs = model(**inputs).logits
lang_id = torch.argmax(outputs, dim=-1)[0].item()
detected_lang = model.config.id2label[lang_id]
# 'eng'
# Arabic
inputs = processor(ar_sample, sampling_rate=16_000, return_tensors="pt").to(model.device)
with torch.no_grad():
outputs = model(**inputs).logits
lang_id = torch.argmax(outputs, dim=-1)[0].item()
detected_lang = model.config.id2label[lang_id]
# 'ara'Чтобы просмотреть все поддерживаемые языки контрольной точки, вы можете вывести идентификаторы языков следующим образом:
processor.id2label.values()
Аудио-предобученные модели
Доступны предобученные модели двух размеров — 300M и 1Bil.
Update on GitHubАрхитектура MMS для ASR основана на модели Wav2Vec2. Дополнительные сведения о дообучении моделей для различных задач см. на странице документации Wav2Vec2.
MMS-TTS использует ту же архитектуру модели, что и VITS, см. страницу документации VITS для справки по API.