Pocketsphinx – розпізнавання мови в реальному проекті

Я не буду докладно розповідати про теорію розпізнавання мови - про це багато і добре написано в інтернеті (наприклад, на тому ж сайті Pocketsphinx). У цій статті я покажу, як вдалося застосувати pocketsphinx у реальному додатку під Android.

І, звичайно, найскладніше у всьому процесі з погляду реалізації — це розпізнавання українських імен та прізвищ в офлайні на величезному розмаїтті Android-пристроїв.

Як розпізнається мова і чому не можна використовувати Google ASR

Коротко: двигун розпізнавання мови (ASR), використовуючи акустичну модель, отримує на вхід дані з мікрофона і на виході повертає гіпотези про те, що говорить користувач у вигляді тексту та деякого цифрового еквівалента точності (confidence). Існує кілька підходів – статистична мовна модель, обмежена граматика запитів та комбінація цих варіантів.

Google ASR надає розпізнавання мовлення на основі великої статистичної моделі мови, що дозволяє розпізнавати мову в так званому режимі диктування. Найбільш добре цей спосіб підходить для пошукових запитів та диктування тексту. Про те, як це працює, докладно розказано в одному з постів Яндекса про SpeechKit. Для такого розпізнавання потрібні великі обчислювальні потужності, тому вони виробляються у хмарі.Googleнадає також “зменшену копію” такого роду моделі для розпізнавання мови в офлайні наJellyBean, завдяки чому можна погано набирати смс-ки, але для розпізнавання всього різноманіття українських імен та прізвищ такий підхід не годиться.

Для цього краще підійде другий метод – розпізнавання на основі обмеженого словника вимов та граматики запитів. При цьому двигун розпізнавання як би знає заздалегідь, що може сказатиКористувач і нічого, крім цього, розпізнати не може. Якщо ваше завдання описує цілком конкретні запити, такий підхід буде найбільш підходящим. Він дозволить підвищити точність розпізнавання саме для конкретного набору слів і зробити це безпосередньо на пристрої без підключення до мережі.

Pocketsphinx під Android

Pocketsphinx- система розпізнавання злитого мовлення - розробляється інженерами з Університету Карнегі-Мелон і компілюється з вихідників до бібліотеки під ARM за допомогою Android NDK. При цьому можна згенерувати JNI-обгортки для використання нативних методів коду наJava.

Поклавши скомпільовану бібліотеку в libs/armeabi проекту, можна завантажити її з коду таким чином:

Основними класами для ініціалізації та роботи з розпізнаванням мови єConfigтаDecoder. За допомогою першого вказуються параметри розпізнавання, а також повні шляхи до мовної моделі, словника вимов і файлу граматики запитів у форматі JSGF (Java Speech Grammar Format). Decoder надає конструктор, який приймає як аргумент цю конфігурацію, і ініціалізує власне інтерфейс для розпізнавання мови.

Для цього можна скористатися методамиstartUtt,processRaw,getHypтаendUtt. Перший і останній відповідно починають і закінчують сесію, а processRaw і getHyp власне розпізнають мову і повертають гіпотези.

Розрахунок confidence після розпізнавання здійснюється за наступною схемою

Що потім дозволяє оцінити, наскільки правильним виявились результати.Гарні значення лежать в області від -3 до 0.

Граматика запитів

Як було сказано раніше, двигунуPocketsphinxможна запропонувати свою граматику у форматіJSGF,яка описує всі можливі фрази. Для завдання розпізнавання імен контактів та деяких команд (типу "Скасувати" або "Перезвонити") використовується такий варіант:

pocketsphinx
Garbage— це те, що дозволяє нам відфільтрувати деякі навколишні шуми, що сприймаються системою як out-of-vocabulary. Як “сміття” я використав усі голосні українські алфавіти. Отже, фраза користувача може починатися і закінчуватися кількома нерозпізнаними звуками, т.к. випливаючи із завдання, користувач починає вимовляти ім'я практично відразу після сигналу і нам заздалегідь відомий приблизний час розпізнавання. Цей підхід допомагає вирішити деякі проблеми, пов'язані з шумом придушення.

Словник вимов

реальному
Він містить відповідність між кожним словом, що бере участь у розпізнаванні, та його транскрипцією, записаною у спеціальному форматі. Є міжнародний фонетичний алфавіт IPA та його ASCII версіяWorldBet. Але формат, що використовується, залежить від самої мовної моделі і в нашому випадку (я використовував українську модель voxforge) він дещо інший. У ньому використовується набір ASCII символів для всіх приголосних, м'яких приголосних, голосних і ударних голосних за наступною схемою: м'які приголосні записуються як подвійний варіант твердого аналога, а ударна голосна - як подвійний ненаголошеною.

Звичайно, неможливо вручну записати транскрипції для всіх видів прізвищ, а також всіляких скорочень. Тому решта варіантів генерується на ходу із застосуванням правил вимови української мови (наприклад, популярне закінчення чоловічих прізвищ -ОВ перетворюється на глуху ay f тощо). Мінус такої генерації в тому, що в деяких випадках вона помиляється, до того ж неможливо проставити правильні наголоси, що знижує точність результатів.розпізнавання.

Згенерувавши файл, що містить транскрипції для всіх імен з наявної контактної книги користувача, можна передати повний шлях у об'єкт класуConfig, також вказавши шляхи до файлу граматики і директорії, що містить дані мовної моделі. Після цього ініціалізувати Decoder і розпочати процес розпізнавання у потрібний момент.

Як отримати дані з мікрофона пристрою

Для цього використається стандартний клас Android SDK AudioRecord. У його конструкторі потрібно вказати тип джерела звуку (стандартний мікрофон, розпізнавання мови, камкодер тощо), частота дискретизації (залежить від моделі, найчастіше це 8 або 16 kHz), формат аудіо-даних та розмірність буфера (також залежить від моделі, що менше тим краще). Варто відзначити, що тип джерела звуку впливає на якість розпізнавання, т.к. операційною системою задіяні деякі можливості оптимізації вихідних даних для кожного конкретного типу (докладніше про це написано в самій документації за класомAudioRecord).

На закінчення

Pocketsphinxнадає можливість використовувати мову в багатьох проектах для мобільних платформ, забезпечуючи прийнятну якість розпізнавання та відносну простоту впровадження.

Звісно, ​​багато проблем залишаються невирішеними. Зокрема в моєму випадку, користувачі часто використовують невимовні імена для деяких контактів (наприклад, абревіатури або однолітерні скорочення), що впливає на якість. Для таких випадків є функціональність створення псевдонімів кожного контакту. Але це теж далеко не все. Різноманітність пристроїв на платформі Android породжує часто різну поведінку на різних девайсах - від швидкості розпізнавання до якості звуку з мікрофона та впливу сторонніх шумів.

Проте продемонстрований підхід дозволив реалізувати реальний продукт, що допомагає здійснювати дзвінки без дотиків до екрану. Спробувати його у справі можна завантаживши на GooglePlay

Із задоволенням відповім на ваші запитання!