Преобразование категориальных данных: Практическое руководство по обработке нечисловых переменных для алгоритмов машинного обучения
В науке о данных существует несколько способов работы с категориальными данными, также известными как данные меток:
- Горячее кодирование
- Кодирование меток
- Фиктивное кодирование
- Биннинг
- Кодировка подсчета
- Частотное кодирование
- Целевое кодирование
Подходящий метод будет зависеть от конкретных данных и целей анализа. Важно отметить, что некоторые алгоритмы, такие как деревья решений и случайный лес, могут напрямую обрабатывать категориальные переменные, поэтому кодирование может не понадобиться.
Теперь мы рассмотрим все вышеперечисленные способы с некоторым набором образцов данных, а также узнаем, как сделать наши данные обучаемыми.
1. Горячее кодирование
Одноразовое кодирование - это метод, используемый для преобразования категориальных переменных в числовые значения путем создания двоичного столбца для каждой категории. Это полезно для обработки категориальных переменных с несколькими уровнями.
Например, предположим, что у нас есть набор данных сумок со столбцом под названием "color", который содержит следующие значения: "red", "green" и "blue".
color | price | units |
red | 500 | 2 |
green | 800 | 3 |
blue | 300 | 1 |
red | 400 | 1 |
green | 600 | 1 |
Однократное кодирование создало бы три новых двоичных столбца, по одному для каждой уникальной категории, со значением 1, указывающим на то, что категория присутствует, и значением 0, указывающим на то, что ее нет. Результирующие данные могут выглядеть следующим образом:
color | price | units | color_red | color_green | color_blue |
red | 500 | 2 | 1 | 0 | 0 |
green | 800 | 3 | 0 | 1 | 0 |
blue | 300 | 1 | 0 | 0 | 1 |
red | 400 | 1 | 1 | 0 | 0 |
green | 600 | 1 | 0 | 1 | 0 |
Как видите, исходный столбец «color» был заменен тремя новыми бинарными столбцами, по одному для каждой уникальной категории. Каждая строка теперь имеет значение 1 ровно в одном из этих новых столбцов, что указывает на наличие этой категории.
Но подождите, у вас должен быть один вопрос..... Как это сделать с помощью python? Итак, давайте сделаем это с помощью python.
В Python вы можете использовать функцию get_dummies()
из библиотеки pandas
, чтобы применить одноразовую кодировку к столбцу "color" вашего фрейма данных. Вот пример того, как это сделать:
import pandas as pd
# Create example dataframe
df = pd.DataFrame({'color': ['red', 'green', 'blue', 'red', 'green'],
'price': [500, 800, 300, 400, 600],
'units': [2, 3, 1, 1, 1]})
# Apply one-hot encoding to "color" column
df_encoded = pd.get_dummies(df, columns=['color'])
print(df_encoded)
В качестве альтернативы вы можете использовать класс OneHotEncoder
из библиотеки sklearn.preprocessing
для применения однократного кодирования.
from sklearn.preprocessing import OneHotEncoder
# Create example dataframe
df = pd.DataFrame({'color': ['red', 'green', 'blue', 'red', 'green'],
'price': [500, 800, 300, 400, 600],
'units': [2, 3, 1, 1, 1]})
# Create an instance of the encoder
encoder = OneHotEncoder(sparse=False)
# Fit and transform the "color" column
color_encoded = encoder.fit_transform(df[['color']])
# Create new dataframe with the encoded values
df_encoded = pd.concat([df.drop(columns=['color']), pd.DataFrame(color_encoded, columns=encoder.get_feature_names(['color']))], axis=1)
print(df_encoded)
Результирующий фрейм данных будет выглядеть так же, как и предыдущий, но столбцы будут иметь префикс 'color_x 0_', а не 'color'.
2. Кодирование меток
Кодирование меток — это метод, используемый для преобразования категориальных переменных в числовые значения путем присвоения каждой категории уникального целочисленного значения. Это полезно для обработки порядковых переменных, где важен порядок категорий.
Например, предположим, что у нас есть набор данных со столбцом под названием "size", который содержит следующие значения: "small", "medium", "large". Кодировка метки заменит каждую категорию целым числом, например: "small" = 0, "medium" = 1, "large" = 2. Результирующие данные могут выглядеть следующим образом:
size | encoded_size |
small | 0 |
medium | 1 |
large | 2 |
small | 0 |
medium | 1 |
Как вы можете видеть, исходный столбец "size" был заменен столбцом "encoded_size", каждая строка теперь имеет уникальное целочисленное значение, представляющее категорию.
Вы можете использовать класс LabelEncoder
из библиотеки sklearn.preprocessing
, чтобы применить кодировку меток к вашим данным. Вот пример того, как это сделать:
from sklearn.preprocessing import LabelEncoder
# Create example dataframe
df = pd.DataFrame({'size': ['small', 'medium', 'large', 'small', 'medium'],
'price': [500, 800, 300, 400, 600],
'units': [2, 3, 1, 1, 1]})
# Create an instance of the encoder
encoder = LabelEncoder()
# Fit and transform the "size" column
df['encoded_size'] = encoder.fit_transform(df['size'])
print(df)
Результирующий фрейм данных, df
, будет иметь новый столбец "encoded_size", представляющий закодированные значения столбца size. Результирующий фрейм данных будет выглядеть следующим образом:
size | price | units | encoded_size |
small | 500 | 2 | 0 |
medium | 800 | 3 | 1 |
large | 300 | 1 | 2 |
small | 400 | 1 | 0 |
medium | 600 | 1 | 1 |
Важно отметить, что кодировка меток изменяет взаимосвязь между категориями. Он присваивает каждой категории уникальный номер, но не учитывает порядковые отношения между категориями. В этом случае закодированные значения "small", "medium" и "large" равны 0, 1 и 2 соответственно, но это не означает, что small вдвое меньше medium или large вдвое больше medium.
3. Фиктивное кодирование
Фиктивное кодирование, также известное как индикаторное кодирование, — это метод, используемый для преобразования категориальных переменных в числовые значения путем создания двоичных столбцов для каждой категории, аналогично горячему кодированию, но при этом не удаляется ни один столбец. Это полезно при работе с категориальными переменными со многими уровнями.
Например, предположим, что у нас есть набор данных со столбцом под названием "color", который содержит следующие значения: "red", "green", "blue". Фиктивное кодирование создало бы три новых двоичных столбца, по одному для каждой уникальной категории, со значением 1, указывающим на то, что категория присутствует, и значением 0, указывающим на то, что ее нет. Результирующие данные могут выглядеть следующим образом:
color | red | green | blue |
red | 1 | 0 | 0 |
green | 0 | 1 | 0 |
blue | 0 | 0 | 1 |
red | 1 | 0 | 0 |
green | 0 | 1 | 0 |
Как вы можете видеть, исходный столбец "color" все еще присутствует в таблице, но были добавлены три новых двоичных столбца, по одному для каждой уникальной категории. Каждая строка теперь имеет значение 1 ровно в одном из этих новых столбцов, что указывает на наличие этой категории.
Вы можете использовать функцию pd.concat()
из библиотеки pandas
, чтобы применить фиктивную кодировку к столбцу "color" вашего фрейма данных, вот пример того, как это сделать:
# Create example dataframe
df = pd.DataFrame({'color': ['red', 'green', 'blue', 'red', 'green'],
'price': [500, 800, 300, 400, 600],
'units': [2, 3, 1, 1, 1]})
# Apply dummy encoding to "color" column
df_encoded = pd.concat([df, pd.get_dummies(df['color'])], axis=1)
print(df_encoded)
Результирующий фрейм данных df_encoded
будет содержать три новых двоичных столбца, по одному для каждой уникальной категории в столбце "color", со значением 1, указывающим на наличие категории, и значением 0, указывающим на ее отсутствие. Исходный столбец "color" все еще присутствует в таблице. Результирующий фрейм данных будет выглядеть следующим образом:
color | price | units | red | green | blue |
red | 500 | 2 | 1 | 0 | 0 |
green | 800 | 3 | 0 | 1 | 0 |
blue | 300 | 1 | 0 | 0 | 1 |
red | 400 | 1 | 1 | 0 | 0 |
green | 600 | 1 | 0 | 1 | 0 |
4. Биннинг
Биннинг — это метод, используемый для группировки числовых значений в ячейки или диапазоны, он используется для обработки числовых переменных с большим количеством уникальных значений. Биннинг может быть полезен для создания категориальных переменных из числовых и для обработки выбросов в данных.
Например, предположим, что у нас есть набор данных со столбцом под названием "age", который содержит следующие значения: 18, 20, 25, 30, 35, 40, 45. Чтобы применить привязку, мы можем разделить диапазон значений на заранее определенное количество интервалов или ячеек. Например, мы можем разделить диапазон возрастов на четыре ячейки: (18, 25], (25, 35], (35, 45], (45, 50]. Это позволило бы сгруппировать возрасты по четырем категориям: "young", "middle-aged", "old" и "very old". Результирующие данные могут выглядеть следующим образом:
age | age_bin |
18 | young |
20 | young |
25 | middle-aged |
30 | middle-aged |
35 | old |
40 | old |
45 | very old |
Как видите, исходный столбец «age» по-прежнему присутствует в таблице, но был добавлен новый столбец «age_bin», который содержит объединенные значения для каждого возраста. Строки в столбце «age_bin» теперь содержат категориальные значения, представляющие возрастную группу.
Вы можете использовать функцию cut()
из библиотеки pandas
, чтобы применить привязку к столбцу "возраст" вашего фрейма данных, вот пример того, как это сделать:
# Create example dataframe
df = pd.DataFrame({'age': [18, 20, 25, 30, 35, 40, 45],
'price': [500, 800, 300, 400, 600, 700, 800],
'units': [2, 3, 1, 1, 1, 2, 3]})
# Apply binning to "age" column
df['age_bin'] = pd.cut(df['age'], bins=[18, 25, 35, 45, 50], labels=['young', 'middle-aged', 'old', 'very old'])
print(df)
Результирующий фрейм данных df
будет иметь новый столбец «age_bin», представляющий объединенные значения столбца age. Результирующий фрейм данных будет выглядеть так:
age | price | units | age_bin |
18 | 500 | 2 | young |
20 | 800 | 3 | young |
25 | 300 | 1 | middle-aged |
30 | 400 | 1 | middle-aged |
35 | 600 | 1 | old |
40 | 700 | 2 | old |
45 | 800 | 3 | very old |
Как видите, исходный столбец «age» по-прежнему присутствует в таблице, но был добавлен новый столбец «age_bin», который содержит объединенные значения для каждого возраста. Строки в столбце «age_bin» теперь содержат категориальные значения, представляющие возрастную группу.
5. Кодирование счета
Кодирование количества - это метод, используемый для преобразования категориальных переменных в числовые значения путем подсчета количества вхождений каждой категории в наборе данных. Он используется для обработки категориальных переменных со многими уровнями.
Например, предположим, что у нас есть набор данных со столбцом под названием "product", который содержит следующие значения: "apple", "orange", "banana", "apple", "orange", "apple", "banana". Кодировка Count заменит каждую категорию количеством раз, когда она появляется в наборе данных. Результирующие данные могут выглядеть следующим образом:
product | count_encoded |
apple | 3 |
orange | 2 |
banana | 2 |
apple | 3 |
orange | 2 |
apple | 3 |
banana | 2 |
Как вы можете видеть, исходный столбец "product" все еще присутствует в таблице, но был добавлен новый столбец "count_encoded", который содержит значения в кодировке count для каждого продукта. Строки в столбце "count_encoded" теперь содержат уникальные целочисленные значения, представляющие количество раз, когда каждый продукт появляется в наборе данных.
Вы можете использовать функцию value_counts()
из библиотеки pandas
, чтобы применить кодировку count к столбцу "product" вашего фрейма данных, вот пример того, как это сделать:
# Create example dataframe
df = pd.DataFrame({'product': ['apple', 'orange', 'banana', 'apple', 'orange', 'apple', 'banana'],
'price': [500, 800, 300, 400, 600, 700, 800],
'units': [2, 3, 1, 1, 1, 2, 3]})
# Apply count encoding to "product" column
df['count_encoded'] = df['product'].map(df['product'].value_counts())
print(df)
Результирующий кадр данных, df
, будет иметь новый столбец «count_encoded», представляющий закодированные значения счетчика столбца продукта. Результирующий фрейм данных будет выглядеть так:
product | price | units | count_encoded |
apple | 500 | 2 | 3 |
orange | 800 | 3 | 2 |
banana | 300 | 1 | 2 |
apple | 400 | 1 | 3 |
orange | 600 | 1 | 2 |
apple | 700 | 2 | 3 |
banana | 800 | 3 | 2 |
6. Частотное кодирование
Частотное кодирование - это метод, используемый для преобразования категориальных переменных в числовые значения путем представления каждой категории как доли встречаемости этой категории в наборе данных. Это похоже на кодировку count, но она нормализует количество путем деления его на общее количество вхождений всех категорий в наборе данных. Он используется для обработки категориальных переменных со многими уровнями.
Например, допустим, у нас есть набор данных со столбцом под названием «product», который содержит следующие значения: «apple», «orange», «banana», «apple», «orange», «apple», «banana». Частотное кодирование заменит каждую категорию количеством раз, которое она появляется в наборе данных. Полученные данные могут выглядеть следующим образом:
product | frequency_encoded |
apple | 0.429 |
orange | 0.286 |
banana | 0.286 |
apple | 0.429 |
orange | 0.286 |
apple | 0.429 |
banana | 0.286 |
Как вы можете видеть, исходный столбец "product" все еще присутствует в таблице, но был добавлен новый столбец "frequency_encoded", который содержит значения в кодировке частоты для каждого продукта. Строки в столбце "frequency_encoded" теперь содержат десятичные значения от 0 до 1, представляющие долю случаев появления каждого продукта в наборе данных.
Вы можете использовать функцию value_counts()
из библиотеки pandas
, чтобы применить частотное кодирование к столбцу "product" вашего фрейма данных, вот пример того, как это сделать:
# Create example dataframe
df = pd.DataFrame({'product': ['apple', 'orange', 'banana', 'apple', 'orange', 'apple', 'banana'],
'price': [500, 800, 300, 400, 600, 700, 800],
'units': [2, 3, 1, 1, 1, 2, 3]})
# Apply frequency encoding to "product" column
df['frequency_encoded'] = df['product'].map(df['product'].value_counts(normalize=True))
print(df)
Результирующий кадр данных df
будет иметь новый столбец «frequency_encoded», представляющий частотно-кодированные значения столбца продукта. Результирующий фрейм данных будет выглядеть так:
product | price | units | frequency_encoded |
apple | 500 | 2 | 0.428571 |
orange | 800 | 3 | 0.285714 |
banana | 300 | 1 | 0.285714 |
apple | 400 | 1 | 0.428571 |
orange | 600 | 1 | 0.285714 |
apple | 700 | 2 | 0.428571 |
banana | 800 | 3 | 0.285714 |
7. Целевое кодирование
Целевое кодирование - это метод, используемый для преобразования категориальных переменных в числовые значения путем представления каждой категории как среднего значения целевой переменной для этой категории. Этот метод используется, когда категориальная переменная имеет большое количество уровней, а также полезен в ситуациях, когда данные сильно несбалансированы.
Например, предположим, что у нас есть набор данных со столбцом под названием «product» и целевой переменной под названием «sales», которая содержит следующие значения:
product | sales |
apple | 100 |
orange | 200 |
banana | 50 |
apple | 150 |
orange | 300 |
apple | 50 |
banana | 20 |
Целевая кодировка заменила бы каждую категорию в столбце "product" средним значением столбца "sales" для этой категории. Результирующие данные могут выглядеть следующим образом:
product | sales | target_encoded |
apple | 100 | 83.333 |
orange | 200 | 250.0 |
banana | 50 | 35.0 |
apple | 150 | 83.333 |
orange | 300 | 250.0 |
apple | 50 | 83.333 |
banana | 20 | 35.0 |
Как вы можете видеть, исходный столбец "product" все еще присутствует в таблице, но был добавлен новый столбец "target_encoded", который содержит целевые значения в кодировке для каждого продукта. Строки в столбце "target_encoded" теперь содержат десятичные значения, представляющие среднее значение столбца "sales" для каждого продукта.
Вы можете использовать функцию groupby()
из библиотеки pandas
, чтобы применить целевую кодировку к столбцу "product" вашего фрейма данных, вот пример того, как это сделать:
# Create example dataframe
df = pd.DataFrame({'product': ['apple', 'orange', 'banana', 'apple', 'orange', 'apple', 'banana'],
'sales': [100, 200, 50, 150, 300, 50, 20]})
# Apply target encoding to "product" column
df['target_encoded'] = df.groupby('product')['sales'].transform('mean')
print(df)
Результирующий фрейм данных, df
, будет иметь новый столбец "target_encoded", представляющий столбец среднего объема продаж для каждого продукта. Результирующий фрейм данных будет выглядеть следующим образом:
product | sales | target_encoded |
apple | 100 | 83.333 |
orange | 200 | 250.0 |
banana | 50 | 35.0 |
apple | 150 | 83.333 |
orange | 300 | 250.0 |
apple | 50 | 83.333 |
banana | 20 | 35.0 |