Границы слогов, расстановка ударения и отображение написания в звук в португальском языке подчиняются правилам, которые лингвисты задокументировали задолго до того, как кто-либо обучил нейросеть. Когда эти правила явны, правильный инструмент — это небольшая, детерминированная, полностью офлайновая библиотека, которую можно прочитать, проверить и запустить где угодно. Именно в этом состоит философия нашего классического стека NLP для португальского: silabificador для слогоделения и TugaPhone для преобразования графемы в фонему (G2P).
Почему классический подход, и почему сейчас
Фонетика — одна из тех областей, где детерминированные правила по-настоящему хороши. Правила слоговых границ португальского языка и закономерности его орфографии хорошо документированы, поэтому написанный вручную механизм правил выдаёт транскрипции, которые можно проверять строка за строкой. Ни GPU, ни загрузки модели, ни сетевых вызовов. Это важно для суверенитета данных: лузофонный голосовой конвейер не должен отправлять свой текст в удалённый API лишь для того, чтобы узнать, как произносится слово. Это важно и для скорости и объёма — эти библиотеки имеют мало зависимостей и одинаково легко работают на ноутбуке, на сервере или на встраиваемом устройстве.
silabificador: границы слогов
silabificador — это лёгкий слогоделитель для португальского, построенный целиком на созданных вручную правилах, без зависимостей. Интерфейс столь же мал, сколь и звучит:
from silabificador import syllabify
syllabify("computador")
# ['com', 'pu', 'ta', 'dor']
Он был настроен и протестирован на чистых данных из Portal da Língua Portuguesa и оценён на Portuguese Phonetic Lexicon — открытом наборе данных из более чем 100 000 записей, взятых из того же источника. Слоговая сегментация — фундаментальный шаг для расстановки ударения, переноса слов и фонемной транскрипции, поэтому сделать её правильно и быстро окупается на всех последующих этапах.
TugaPhone: графема-в-фонему с учётом диалекта
TugaPhone преобразует произвольный португальский текст в IPA, и делает это для основных лузофонных диалектов: европейского (pt-PT), бразильского (pt-BR), ангольского (pt-AO), мозамбикского (pt-MZ) и тиморского (pt-TL). Что принципиально, он сохраняет диалектную вариативность, а не сглаживает всё до единого «стандарта». Одно и то же предложение звучит по-разному в зависимости от того, где на нём говорят:
Choveu muito ontem à noite.
pt-PT → ʃuˈvew ˈmũjtu ˈõtɐ̃j a ˈnojt
pt-BR → ʃoˈvew ˈmwĩtʊ ˈõtẽj a ˈnojtʃɪ
pt-AO → ʃoˈvew ˈmũjntʊ ˈõntẽj a ˈnojtɨ
pt-MZ → ʃoˈvew ˈmũjtu ˈõtẽj a ˈnɔjtɨ
pt-TL → ʃoˈvew ˈmujtʊ ˈõntɐ̃j a ˈnojtʰ
Под капотом TugaPhone задействует общий движок решётки кандидатов orthography2ipa и надстраивает над ним специфичные для португальского аспекты через собственные точки расширения этого движка. Он обращается к тщательно составленному фонетическому лексикону (тому же Portuguese Phonetic Lexicon, что и выше) для известных слов; для всего, чего нет в лексиконе, — имён, неологизмов, иностранных заимствований — решётка порождает кандидатов на основе графемных и аллофонных правил диалекта.
Стоит выделить две детали. Нормализация чисел превращает цифры в их произносимые португальские формы с правильным согласованием рода и числа:
from tugaphone.number_utils import normalize_numbers
normalize_numbers("vou comprar 1 casa") # uma casa
normalize_numbers("vou adotar 2 cães") # dois cães
Он даже соблюдает соглашения о масштабе — длинная шкала biliões для pt-PT, короткая шкала trilhões для pt-BR. Разрешение неоднозначности омографов делегировано библиотеке bifonia, которая владеет знанием на уровне значений о том, какие гетерофонные омографы существуют и какое чтение они несут, — поэтому para как предлог обрабатывается иначе, чем para как глагол — и помечает выбранное чтение дополнительными диакритиками ещё до того, как предложение попадёт в решётку.
TugaPhone фонемизирует, задействуя общую решётку кандидатов orthography2ipa: выбор диалекта и есть выбор спецификации лекта orthography2ipa, поэтому диалектные явления — бетацизм, восходящие дифтонги Порту, палатализация /l/ в Мадейре, фронтирование /u/ на Азорах, сандхи конечных сибилянтов и другое — исходят из самой решётки, а не из постобработки строк. TugaPhone добавляет только то, что orthography2ipa намеренно оставляет на усмотрение вызывающего кода, подключаясь через собственные точки расширения движка: учитывающее род расширение чисел/порядковых числительных и разметка гетерофонов bifonia выполняются на этапе нормализации движка ещё до того, как решётка увидит текст; курируемый лексикон произношения из Tugalex регистрируется для каждого лекта через orthography2ipa.register_lexicon, так что покрытое слово попадает на тот же путь переопределения, что и собственные исключения спецификации, а решётка порождает кандидатов только для слов, не покрытых лексиконом; слогоделение поступает из собственного плагина orthography2ipa на основе silabificador, так что ударение падает на тот же слог, который иначе выбрал бы сам TugaPhone. Небольшие, компонуемые части, питающие общий движок, — каждая полезна сама по себе.
TugaPhone честен относительно своих пределов: покрытие лексикона беднее для африканских и тиморского диалектов, субрегиональные акценты (Порту, Минью, Брага и другие) — это экспериментальные приближения документированных особенностей, а просодия на уровне предложения упрощена. Это открыто документированные ограничения, а не скрытые режимы сбоя.
Более широкая картина: orthography2ipa
Португальский — лишь один вариант среди многих, и тот же инженерный паттерн обобщается. orthography2ipa — это Python-пакет из чистых данных с лингвистически мотивированными отображениями графема→IPA и аллофонов, охватывающими 820 языков из более чем 20 языковых семей. Он проводит чёткое различие, которое необходимо любой серьёзной системе G2P: карта графем говорит, какие фонемы написание может представлять, тогда как карта аллофонов говорит, как фонема на самом деле реализуется в данном контексте. Региональные варианты моделируются как собственные спецификации, связанные через взвешенную родословную с несколькими предками, поэтому диалектные деревья наследуют от своих родителей вместо дублирования данных.
Это тот же инстинкт, что стоит за pt-PT, pt-BR, pt-AO, pt-MZ и pt-TL в TugaPhone: относиться к каждому лузофонному варианту как к полноправному гражданину с собственными правилами, а не как к отклонению от единственного канонического акцента. Данные декларативны, а логика тонка и подключаема — можно прочитать правила, сослаться на их источники и доверять результату.
Попробуйте
Всё, что здесь есть, — открытый исходный код, и его можно установить уже сегодня:
pip install tugaphone
pip install git+https://github.com/TigreGotico/silabificador
Что касается более широких многоязычных отображений, см. orthography2ipa. Детерминированный, быстрый, офлайновый и созданный для всей широты португалоязычного мира.
Этот стек португальской фонетики опирается на нашу работу по преобразованию графемы в IPA для 820 языков, образуя фонетический костяк для TTS, который работает на картошке и многоязычных голосов Miro и Dii.