Пошаговое руководство с примерами кодирования.

Что такое обработка естественного языка?

Обработка человеческого языка (который может быть в форме текста или голоса) для извлечения полезной информации или использования информации для создания человеческого языка известна как обработка естественного языка (NLP).

Одними из самых популярных инструментов НЛП являются Google Translate и Siri. Google Translate понимает заданный язык, обрабатывает его и переводит на другой человеческий язык. Siri похожа, но использует распознавание речи для понимания человеческого языка и выводит информацию в голосовой форме. Чат-боты — еще один мощный инструмент, использующий НЛП. Чат-бот может использоваться банковской фирмой для взаимодействия со своими клиентами. Тем не менее, NLP все еще открыт для улучшений, и поэтому ни Siri, ни Google Translate, ни чат-боты не идеальны.

Основная логика, которую использует НЛП, заключается в том, что каждая информация будет сужаться до предложений, предложения будут сужаться до слов, а слова будут сужаться до основ слов. В идеале наша модель будет получать общую информацию, постепенно просматривая их.

Одна из проблем работы с текстовыми или голосовыми данными заключается в том, что машины не могут понять человеческий язык, поэтому нам необходимо преобразовывать наши данные в числа. Библиотеки NLP будут преобразовывать слова в векторы, чтобы мы могли передавать эти данные в различные модели машинного обучения.

Еще одна проблема заключается в том, что лингвистический состав каждого языка различен, поэтому применение инструментов НЛП к каждому языку также будет происходить по-разному. Например, вы можете образовать разные слова из одной основы, добавив последовательность суффиксов на турецком языке. Как видно из примера слева, предложение «I can't do» выражается одним глаголом, имеющим собственное значение, в отличие от английского. Таким образом, для каждого языка будут разные решения НЛП.

Чтобы понять НЛП на примере кода, я сначала представлю анализ настроений. Анализ настроений — это подраздел НЛП, который может помочь нам понять эмоции, скрытые в человеческом языке, и принимать решения на основе данных.

Анализ настроений может быть полезен для понимания общего мнения публики. Например, различные правительства могут использовать анализ настроений, просматривая такие ресурсы, как твиты и статьи, для корректировки своей политики. (На самом деле, классификация твитов и анализ эмоций, основанные на твитах с упоминанием Трампа и Байдена, являются популярными проектами НЛП для начинающих).

Анализ настроений также можно использовать для принятия разумных бизнес-решений. Например, приложение для медитации Calm может просмотреть обзоры в Google Play Store, чтобы понять, какие функции приложения больше всего любят или ненавидят, и внести необходимые изменения на основе этой информации.

Анализ настроений можно использовать в следующих областях:

  • Маркетинг
  • Финансы
  • Социальные медиа
  • Обзоры приложений
  • Бизнес-аналитика

Пример кодирования

Пример будет охватывать следующие термины:

  • Токенизация слов
  • Облако слов
  • TF-IDF
  • Мешок слов
  • Разреженная матрица

Давайте посмотрим на набор данных из обзоров приложений. Я проведу анализ настроений в этом наборе данных, чтобы понять отзывы клиентов и выяснить, нужны ли какие-либо изменения в приложении.

Предварительная обработка

Очистка данных

Мы должны сначала очистить данные. Обзоры будут на человеческом языке, поэтому будут смайлики, аббревиатуры и сленговые слова.

df.drop("Unnamed: 0", axis = 1, inplace = True)
df['year'] = pd.DatetimeIndex(df['date']).year
df['month'] = pd.DatetimeIndex(df['date']).month
df['day'] = pd.DatetimeIndex(df['date']).day
df = df.drop(columns=["date"])
df.head()

Первый инструмент, который я представлю, — это токенизация слов. Токенизация слов разделит предложения на слова, что поможет нам преобразовать большие фрагменты текста в токены.

Количество слов в обзоре может быть полезной информацией, поэтому я добавлю его в виде столбца во фрейм данных.

from nltk import word_tokenize
word_token = [word_tokenize(review) for review in df.review]
len_tokens= [] 

for i in range(len(word_token)):
    len_tokens.append(len(word_token[i]))

df["n_tokens"] = len_tokens

Я переведу все отзывы в нижний регистр и уберу знаки препинания. Это необходимо, так как начало предложения или имена собственные не имеют существенного значения в нашем примере и поскольку знаки препинания могут мешать работе библиотек НЛП, которые мы будем использовать далее.

df['review'] = df['review'].str.replace('[^\w\s]','')
df['review'] = df['review'].str.lower()
df.head()

Анализ отзывов

Облако слов

Мы можем использовать облака слов, чтобы визуализировать, какие слова чаще всего использовались в обзоре. В этом конкретном примере я рассмотрю обзоры с рейтингом 1. Понимание того, какие слова использовали пользователи, поставившие рейтинг 1, может помочь выяснить, какие функции вызывают наибольшее количество жалоб.

Стоп-слова — это слова, которые часто встречаются в тексте и не имеют определенного значения (примеры: 'the', 'a', a и 'есть'). В зависимости от набора данных могут быть некоторые слова, которые часто используются в нашем наборе данных, но не являются стоп-словами. Например, слово "приложение" не является стоп-словом, поскольку оно имеет значение. Однако в нашей интерпретации это не будет иметь особого значения, поскольку мы смотрим на набор данных отзывов о приложениях, где слово приложение присутствует в различных рейтингах. Таким образом, я обновлю стоп-слова и добавлю 'приложение' в качестве стоп-слова, чтобы не видеть 'приложение' в своем облаке слов. как это обычно упоминалось.

# choose the df where rating is 1
df_1 = df[(df["rating"] == 1)]
text_1 = " ".join(review for review in df_1.review)
# initialize stop words
stopwords = set(STOPWORDS)
# setting our own stopwords
stopwords.update(["meditation", "app", "meditate", "im", "meditations" ,"thing", "calm", "dont", "really"])
# create the wordcloud 
cloud_1 = WordCloud(stopwords=stopwords, background_color="white").generate(text_1)

Внедрение TF-IDF

Я не буду подробно объяснять TF-IDF, так как я уже рассказывал об этом в этом посте.

vect = TfidfVectorizer(max_features = 10, stop_words=stopwords)
tfIdf = vect.fit(df_1.review)
X = vect.transform(df_1.review)
X_df = pd.DataFrame(X.toarray(), columns = vect.get_feature_names())
X_df.head()

Мешок слов

Bag of Words будет просто представлять предложения как количество вхождений слов и преобразовывать текст в векторы.

Допустим, у нас есть следующие предложения:

  • Эта книга великолепна.
  • Эта книга потрясающая.
  • Эта книга не велика.

У нас есть уникальные слова ['Это', 'книга', 'есть', 'великолепно', 'удивительно', 'нет']. В представлении BoW предложения будут представлены в виде векторов:

  • Эта книга великолепна. → [1, 1, 1, 1, 0, 0]
  • Эта книга потрясающая. → [1,1,1,0,1,0]
  • Эта книга не велика. → [1,1,1,1,0,1]

Причина, по которой это называется «мешок», заключается в том, что слова расположены не в определенном порядке, поэтому создается впечатление, что все слова были брошены в мешок.

Возвращаясь к нашему примеру с обзорами приложений, мы можем вычислить BoW, используя CountVectorizer из библиотеки scikit-learn. Следовательно, мы используем другую библиотеку стоп-слов для вычисления BoW.

my_stopwords = ENGLISH_STOP_WORDS

Внутри CountVectorizer мы можем указать, сколько n_grams мы хотим, то есть мы можем решить, хотим ли мы смотреть на каждое слово по одному или на группы из n элементов. Если мы укажем n_grams равным 2, мы также будем рассматривать предложение Эта книга не велика как фрагменты слов [Эта книга, не, не велика, книга]. Следует отметить, что теперь у нас нет путаницы с интерпретацией отлично как положительной эмоции в предложении, поскольку оно сгруппировано с не очень в 2 граммах. Пожалуйста, ознакомьтесь с документацией для более подробной информации о входных данных CountVectorizer.

vectorizer = CountVectorizer(ngram_range=(1,3), max_features = 100, max_df=500, stop_words= my_stopwords)
vectorizer.fit(df_1.review)
X = vectorizer.transform(df_1.review)
X_df = pd.DataFrame(X.toarray(), columns= vectorizer.get_feature_names())
X_df

Вычисляя BoW, мы видим, что получили огромный фрейм данных с большим количеством вхождений 0. Наш фрейм данных огромен, потому что у нас есть много слов, которые не повторяются в предложениях, поэтому длина наших векторов увеличилась. Высокие вхождения 0 показывают, что у нас есть разреженная матрица, то есть матрица, в которой большинство элементов равны нулю.

Мы можем использовать все эти инструменты, чтобы делать выводы на основе наших данных. Смотрите полный код.

Спасибо за чтение! Я хотел бы услышать от вас, если у вас есть какие-либо предложения 🧚🏼‍♂️