После того, как мы закончили веб-парсинг (процесс извлечения данных из источника), у нас есть данные, но в неструктурированной или необработанной форме (или в неочищенной форме). Что нам нужно сделать сейчас, так это очистить наши данные, чтобы мы могли исследовать дальше.

Согласно IBM Data Analytics, вы можете потратить до 80% своего времени на очистку данных.

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

Выявление отсутствующих значений в наборе данных

Прежде чем приступить к любому EDA (исследовательскому анализу данных) наших данных, нам нужно проверить, есть ли в нашем наборе данных отсутствующие значения или нет. Для нашего удобства давайте создадим фрейм данных вручную.

import pandas as pd
import numpy as np
data = pd.DataFrame({‘Gender’:[‘Male’,‘Male’,np.NaN,’Female’,‘Male’,‘Female’,np.Nan,‘Male’,‘Male’,np.Nan],‘Age’: [23,25,27,22,np.Nan,26,np.Nan,25,np.Nan,212]})

Теперь фрейм данных выглядит примерно так:

Наш фреймворк состоит из двух функций. Один из них - это «Пол», категориальная характеристика (тип характеристики, значения которой можно разделить на группы), а другой - «Возраст», непрерывная характеристика (которая может принимать бесконечное количество значений между любыми двумя значениями). Мы видим, что в нашем наборе данных есть некоторые отсутствующие значения (NaN - Not a Number), и мы легко это выяснили. Но в некоторых наборах данных есть несколько наблюдений (или записей или строк), и невозможно подсчитать количество пропущенных значений вручную для каждой функции (или поля или столбца). Здесь в игру вступает библиотека Pandas. Достаточно легко найти недостающие значения в наборе данных, имеющем большее количество наблюдений, с помощью всего одной строчки кода Pandas.

Посмотрим, как это работает в нашем случае.

dataset.isna().sum()

Вот и все. Ура! Мы сделали это! Но недостатком этого метода является то, что он работает только тогда, когда отсутствует значение np.NaN. Бывают случаи, когда отсутствующие значения равны 0 или что-то в этом роде, в зависимости от характеристик набора данных. В этом случае мы можем использовать метод Pandas value_counts ().

for column in dataset.columns:
    if (dataset[column].value_counts().sort_index().head(1).index == 0):
   print(dataset[column].value_counts().sort_index().head(l).values)
1)

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

Обработка и вменение пропущенных значений

Существует несколько способов обработки и вменения отсутствующих значений в нашем наборе данных в зависимости от типа объекта. Во-первых, нам нужно проверить долю данных, которые отсутствуют в функции, относительно общего количества значений в этой функции. Я бы посоветовал, если более 40% значений в функции отсутствует, просто удалите эту функцию из набора данных. Это не правило большого пальца или что-то в этом роде. Это кое-что из моих наблюдений. Опять же, Pandas помогает нам найти долю пропущенных значений в функции.

for column in dataset.columns:
    print(dataset[column].value_counts(normalize=True, dropna=False)*100
    print('-------------------------------------------------------')

В нашем случае результат будет таким:

Ссылаясь на индекс «NaN», наш набор данных содержит 30% отсутствующих значений в обеих функциях. Наша работа легко выполняется с помощью Pandas. В этом вся прелесть панд. Если для какой-либо из функций кажется, что отсутствует более 40% данных, мы можем просто исключить эту функцию из нашего набора данных. Опять же, я говорю, что это не правило большого пальца. Если вы уверены, что можете приписать эти 40% или более отсутствующих значений несколько точным значениям, вы можете следовать своей стратегии.

Теперь есть несколько стратегий для вменения недостающих данных в некоторые значимые значения в нашей функции. Мы не можем просто так приписать недостающие данные некоторым случайным значениям. В Scikit-Learn есть несколько предопределенных стратегий для вменения пропущенных значений. Они бывают "средние", "средние", "наиболее частые" и "постоянные". Нам необходимо реализовать эти стратегии в зависимости от типа функции, которую мы собираемся обрабатывать. Есть два случая обработки пропущенных значений.

Случай 1. Работа с категориальной функцией

Давайте рассмотрим тот же набор данных, который мы использовали в предыдущем разделе. Здесь одна из характеристик, известная как «Пол» с 10 наблюдениями, имеющими значения «Мужской» или «Женский», является категориальной характеристикой. В функции «Пол» отсутствует несколько наблюдений, и мы хотим восполнить эти недостающие значения (NaN) с помощью некоторой стратегии. Поскольку наша функция является категориальной, нам необходимо заполнить отсутствующие значения, используя стратегию под названием «наиболее_частотный» (т. Е.) Приписывание пропущенных значений наиболее часто встречающейся группе. В нашем случае имеется 5 значений с группой «Мужской» и 2 значения с «Женщиной». Пропущенные значения (или) NaN заменяются на «Male». Довольно просто, не правда ли?

Мы можем добиться этого с помощью SimpleImputer Scikit-Learn (sklearn.impute.SimpleImputer).

from sklearn.impute import SimpleImputer
imp = SimpleImputer(missing_values=np.nan, strategy='most_frequent')
dataset['Gender'] = pd.DataFrame(imp.fit_transform(np.array(dataset['Gender']).reshape(-1,1)))

Случай 2. Работа с непрерывной функцией

В этом случае мы попробуем две стратегии, такие как «среднее» и «медиана». Давайте сначала обсудим «среднее», затем ограничение использования «среднего» и то, как «медиана» преодолевает ограничение «среднего».

(i) «среднее» в качестве стратегии вменения:

Как мы все знаем, «среднее» - это просто «среднее», к которому мы привыкли, когда мы складываем все числа, а затем делим на количество чисел. Здесь мы сделаем то же самое. Мы вычисляем среднее значение существующих значений и заменяем отсутствующие значения вычисленным средним значением. Давайте узнаем среднее значение для нашей функции «Возраст».

Среднее значение составляет около 51,42. (т.е.) (23 + 25 + 27 + 22 + 26 + 25 + 212) / 7 = 360/7 = 51,428.

Теперь мы можем использовать ту же самую вмененную библиотеку Scikit-Learn, установив параметр стратегии SimpleImputer как «среднее».

from sklearn.impute import SimpleImputer
imp = SimpleImputer(missing_values=np.nan, strategy='mean')
dataset['Gender'] = pd.DataFrame(imp.fit_transform(np.array(dataset['Gender']).reshape(-1,1)))

Теперь результат после подстановки пропущенных значений (в обеих функциях) будет примерно таким:

Чего ждать? Это так? Среднее значение 51,42? Конечно да. Но как это могло иметь значение? Возраст большинства наблюдений составляет около 22–26 лет, за исключением последнего, которому исполнилось 212 года. Это здорово! Ошибки такого типа часто можно увидеть в реальных наборах данных, где есть вероятность человеческих ошибок. Возраст последнего может быть 21. Из-за некоторой ошибки, связанной с человеческим фактором (опечатка), он может стать 212. Такие значения часто известны как выбросы. Если принять во внимание правильный возраст (21) и вычислить среднее значение, мы можем получить среднее значение где-то около 24–25, что вполне разумно. Из-за одного ненормального значения в функции влияет на все распространение функции. Это ограничение использования «среднего» в качестве стратегии вменения. Давайте посмотрим, как «медиана» решает эту проблему.

(ii) «медиана» как стратегия вменения:

«Медиана» - это «среднее» значение в списке чисел. Чтобы найти медиану, числа должны быть перечислены в числовом порядке от наименьшего к наибольшему, поэтому нам, возможно, придется переписать список, прежде чем мы сможем найти медиану. Если количество значений в списке нечетное, мы просто рассматриваем среднее значение как «медианное». Если количество значений в списке является медианным, нам нужно взять «среднее» из двух средних значений и рассматривать полученное значение как «медианное». Так работает медиана. Давайте попробуем найти «медианное» значение для нашей функции «Возраст».

Среднее значение параметра «Возраст» составляет 25,0. Ах! мы сделали это! В этом есть смысл по сравнению со «средним», равным 51,42! Давайте представим себе, как мы получили это решение. Сначала мы располагаем значения в порядке возрастания (то есть от меньшего к большему).

22, 23, 25, 25, 26, 27, 212

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

Теперь давайте вменим недостающие значения с помощью «медианы» в качестве стратегии.

from sklearn.impute import SimpleImputer
imp = SimpleImputer(missing_values=np.nan, strategy='median')
dataset['Gender'] = pd.DataFrame(imp.fit_transform(np.array(dataset['Gender']).reshape(-1,1)))

Результирующий фрейм данных будет:

Таким образом, это всегда зависит от особенности набора данных. Если есть набор данных с большими выбросами, я предпочитаю «медианное». Например. 99% дохода семьи ниже 100, а 1% выше 500. С другой стороны, если мы работаем с ношением одежды, которую клиенты отдают в химчистку (при условии, что операторы химчистки заполняют это поле интуитивно) , Я заполню пропущенные значения "средним" значением износа.

Бонус:

В последней версии Scikit-Learn, которая является версией 0.22, представлен новый способ вменения отсутствующих значений путем прогнозирования отсутствующих значений с помощью алгоритма машинного обучения, известного как «k-Nearest Neighbours».

Хотите узнать о k-ближайших соседях? Взгляните на это - Основы машинного обучения с алгоритмом K-ближайших соседей

Если вы заинтересованы в изучении Pandas, я бы посоветовал качественный контент из плейлиста Кевина Маркхэма Анализ данных в Python с помощью pandas, который содержит более 30 видео. В конце каждого видео он давал несколько бонусных советов с кристально ясным объяснением, и мне нравится его видео 25 лучших трюков в пандах.

Если у вас есть какие-либо вопросы, предложения или идеи, свяжитесь со мной по адресу [email protected]. Кроме того, вы можете проверить мои репозитории GitHub, чтобы увидеть больше кода и проектов по машинному обучению. Любые предложения приветствуются.