Библиотеки Python. Часть 4. Морфология
Библиотека pymorphy2
Вы уже знаете стандартные строковые функции и пользовались ими. Мы умеем работать со строками посимвольно и знаем, как представляется текстовая информация. Давайте перейдем на уровень выше. Строка и текст в общем случае состоят не из набора букв, а из слов, и иногда нужно работать именно со словами, а не просто с последовательностями байтов.
Возьмем для примера склонение существительных с числительными. Например, на форуме надо написать, что в теме «21 комментарий», но «24 комментария». То же самое нужно делать и для других слов: например, «новость», «пользователь». Иногда на сайтах обходят эту проблему и вставляют машинное «комментариев: 21».
Довольно много статей на эту тему. Например, эта.
Давайте посмотрим, какие средства работы со словами есть в Python, и познакомимся с библиотекой pymorphy2
(морфология).
Если эта библиотека отсутствует в вашем Python, ее надо установить с помощью утилиты pip
.
Словари распространяются отдельными пакетами. Для русского языка используется pymorphy2-dicts-ru
.
Они обновляются время от времени, для обновления используйте команду
Морфологический анализ
В pymorphy2
для морфологического анализа слов есть класс MorphAnalyzer
.
Морфологический анализ — определение характеристик слова на основе того, как оно пишется. При морфологическом анализе не учитываются соседние слова.
Для любого слова библиотека делает несколько предположений, что оно может означать, и обозначает свою уверенность в этом предположении.
Метод MorphAnalyzer.parse()
возвращает один или несколько объектов типа Parse
с информацией о том, как слово может быть разобрано.
В данном случае предположение одно с уверенностью score=1.0
. Итак, мы имеем дело с существительным NOUN
, именем собственным, одушевленным, мужского рода. Конечно, предположений может быть несколько:
У каждого разбора есть тег:
Тег
Тег — набор граммем (грамматических признаков), характеризующих данное слово.
Например, тег 'VERB,impf, tran femn, sing,past,indc
' означает, что слово — глагол (VERB
) несовершенного вида (impf
), переходный (tran
), женского рода (femn
), единственного числа (sing
), прошедшего времени (past
), изъявительного наклонения (indc
).
Полный список граммем (грамматических единиц) можно посмотреть тут и тут.
Работа с тегами
Чтобы проверить, есть ли в данном теге отдельная граммема (или все граммемы из указанного множества), используйте оператор in
:
Пример:
Кроме того, у каждого тега есть атрибуты, через которые можно получить часть речи, число и другие характеристики:
Если мы попытаемся получить доступ к граммеме, которой нет для слова данной части речи, получим None
.
Итак, мы можем разбирать большие тексты на части и узнавать информацию о словах: например, искать глаголы, подсчитывать имена и т. д.
Для изменения слов (к примеру, склонения существительных) можно использовать метод inflect
:
И во множественном числе:
Метод inflect
работает и с другими частями речи — например, глаголами:
Вернемся к параметру score
.
Мы видим, что предложенные четыре варианта разбора имеют параметр score, который говорит нам о том, какой вариант предпочтительнее. Pymorphy2 использует статистические методы и ориентируется на данные проекта OpenCorpora, чтобы вычислить значение параметра score
. Мы не будем останавливаться на этом подробно. Интересующиеся могут прочитать о внутренней кухне на странице документации по Pymorphy2. Скажем только, что эти вычисления не всегда точны.
Разборы сортируются по убыванию score, поэтому почти везде в примерах берется первый вариант разбора из возможных (например, morph.parse('пила')[0]
).
Постановка слов в начальную форму
Нормальную (начальную) форму слова можно получить через атрибуты Parse.normal_form
и Parse.normalized
. Например, для глаголов в нем будет храниться инфинитив. Таким образом, можно привести любую форму глагола к единому виду.
Но что считается за нормальную форму у других слов? Например, возьмем слово «изучающим». Иногда мы захотим нормализовать его в «изучать», иногда — в «изучающий», иногда — в «изучающая».
Посмотрим на примере, что сделает pymorphy2
:
Pymorphy2
сейчас использует алгоритм нахождения нормальной формы, который работает наиболее быстро (берется первая форма в лексеме) — именно поэтому, например, все причастия сейчас нормализуются в инфинитивы. Это можно считать деталью реализации.
Если требуется нормализовать слова иначе, можно воспользоваться методом Parse.inflect()
:
Согласование с числительными
Помимо разбора слов, библиотека может их изменять — например, сопоставлять с числами. Давайте посмотрим, как можно решить задачу с подсчетом и выводом количества комментариев на форуме:
Интересно, что библиотека пытается работать даже со словами, которых не знает, обращаясь к оракулу: