Добро пожаловать на мою среднюю страницу! В этом посте я проанализирую данные о маркетинговых исследованиях и рекомендациях по продажам спортивного магазина. Данные, которые будут использоваться в этом исследовании, получены из одного из модулей DQLAB «Аналитик данных: исследование бизнес-решений». Есть несколько шагов для анализа данных, включая подготовку данных, визуализацию и создание модели с использованием логистической регрессии, чтобы помочь бизнес-решениям в будущем.
О НАБОРЕ ДАННЫХ
Доступ к набору данных можно получить по адресу: https://storage.googleapis.com/dqlab-dataset/data_retail.csv
Набор данных Продажи спортивного центра DQLAB, спортивный магазин. такие как baju, jaket, tas и sepatu продаются с 2013 года. В начале 2019 года количество покупателей, вернувшихся в магазин, уменьшилось. Клиентов, которые не возвращаются в течение шести месяцев после покупки, можно определить как отток.
Набор данных содержит данные о продажах с 2013 по 2019 год в файле CSV с 8 столбцами: No, Row_Num, Customer_ID, Product, First_Transaction, Последняя_транзакция, Средняя_сумма_транзакции, Количество_транзакций.
ПОДГОТОВКА ДАННЫХ
Импорт данных
Во-первых, мы можем импортировать данные CSV с помощью pandas.
import pandas as pd df = pd.read_csv('https://storage.googleapis.com/dqlab-dataset/data_retail.csv', sep=';')
Очистка данных
На этом этапе мы изменим тип данных, чтобы упростить обработку данных. Мы можем начать с изменения типа данных для столбцов First_Transaction и Last_Transaction на datetime64 с помощью следующих команд:
# First_Transaction df['First_Transaction'] = pd.to_datetime(df['First_Transaction']/1000, unit='s', origin='1970-01-01') # Last_Transaction df['Last_Transaction'] = pd.to_datetime(df['Last_Transaction']/1000, unit='s', origin='1970-01-01')
Отток клиентов
На этом шаге мы классифицируем клиента, который является отчужденным покупателем, покупателем, который не возвращается в магазин через шесть месяцев. Мы можем отделить отток, найдя последнюю транзакцию клиента и классифицировав, какие клиенты были включены в отток.
print(max(df['Last_Transaction'])) df.loc[df['Last_Transaction'] <= '2018-08-01', 'is_churn'] = True df.loc[df['Last_Transaction'] > '2018-08-01', 'is_churn'] = False
После этого можем удалить ненужные столбцы
del df['no'] del df['Row_Num']
ВИЗУАЛИЗАЦИЯ ДАННЫХ
Сбор данных по годам
На этом этапе мы визуализируем тенденцию привлечения клиентов по годам с помощью гистограммы. Давайте создадим новый столбец для First_Transaction и Last_Transaction, а именно Year_First_Transaction и Year_Last_Transaction, чтобы получить год бара. И мы можем визуализировать это с помощью команд ниже:
import matplotlib.pyplot as plt df['Year_First_Transaction'] = df['First_Transaction'].dt.year df['Year_Last_Transaction'] = df['Last_Transaction'].dt.year df_year = df.groupby(['Year_First_Transaction'])['Customer_ID'].count() df_year.plot(x='Year_First_Transaction', y='Customer_ID', kind='bar', title='Graph of Customer Acquisition') plt.xlabel('Year_First_Transaction') plt.ylabel('Num_of_Customer') plt.tight_layout() plt.show()
Из графика видно, что самый высокий покупательский спрос у магазина был в 2017 году.
Сделка по годам
На этом этапе мы визуализируем транзакцию по годам с помощью гистограммы. Мы можем визуализировать с помощью команд ниже:
import matplotlib.pyplot as plt plt.clf() df_year = df.groupby(['Year_First_Transaction'])['Count_Transaction'].sum() df_year.plot(x='Year_First_Transaction', y='Count_Transaction', kind='bar', title='Graph of Transaction Customer') plt.xlabel('Year_First_Transaction') plt.ylabel('Num_of_Transaction') plt.tight_layout() plt.show()
Средняя сумма транзакции по годам
Чтобы увидеть среднее количество транзакций за год, мы можем визуализировать данные с помощью линии графика, чтобы мы могли видеть рост продукта. Чтобы визуализировать среднюю транзакцию, мы можем использовать команды:
plt.clf() sns.pointplot(data = df.groupby(['Product', 'Year_First_Transaction']).mean().reset_index(), x='Year_First_Transaction', y='Average_Transaction_Amount', hue='Product') plt.tight_layout() plt.show()
Взбитая доля
Давайте посмотрим долю оттока клиентов в каждом продукте, используя круговую диаграмму.
import matplotlib.pyplot as plt plt.clf() # Melakukan pivot data dengan pivot_table df_piv = df.pivot_table(index='is_churn', columns='Product', values='Customer_ID', aggfunc='count', fill_value=0) # Mendapatkan Proportion Churn by Product plot_product = df_piv.count().sort_values(ascending=False).head(5).index # Plot pie chartnya df_piv = df_piv.reindex(columns=plot_product) df_piv.plot.pie(subplots=True, figsize=(10, 7), layout=(-1, 2), autopct='%1.0f%%', title='Proportion Churn by Product') plt.tight_layout() plt.show()
Как видно из диаграммы, на каждый продукт уходит более 50% клиентов.
Распределение клиентов по количеству транзакций
На этом этапе мы разделим клиентов на 5 групп в зависимости от количества транзакций.
Мы будем визуализировать данные с помощью гистограммы, чтобы увидеть распределение клиентов в транзакции, используя команды ниже:
plt.clf() def func(row): if row['Count_Transaction'] == 1: val = '1. 1' elif (row['Count_Transaction'] >1 and row['Count_Transaction'] <= 3): val ='2. 2 - 3' elif (row['Count_Transaction'] >3 and row['Count_Transaction'] <= 6): val ='3. 4 - 6' elif (row['Count_Transaction'] >6 and row['Count_Transaction'] <= 10): val ='4. 7 - 10' else: val ='5. >10' return val # Tambahkan kolom baru df['Count_Transaction_Group'] = df.apply(func, axis=1) df_year = df.groupby(['Count_Transaction_Group'])['Customer_ID'].count() df_year.plot(x='Count_Transaction_Group', y='Customer_ID', kind='bar', title='Customer Distribution by Count Transaction Group') plt.xlabel('Count_Transaction_Group') plt.ylabel('Num_of_Customer') plt.tight_layout() plt.show()
Как мы видим на графике, распределение покупателей, совершающих транзакции только один раз, имеет наибольшее число, из чего можно сделать вывод, что покупатели обычно не возвращаются в магазин после совершения первой транзакции.
Распределение средней суммы сделки
На этом этапе мы разделим клиентов на 8 групп в зависимости от суммы транзакции.
Мы будем визуализировать данные с помощью гистограммы, чтобы увидеть распределение клиентов в транзакции, используя команды ниже:
def f(row): if (row['Average_Transaction_Amount'] >= 100000 and row['Average_Transaction_Amount'] <=250000): val ='1. 100.000 - 250.000' elif (row['Average_Transaction_Amount'] >250000 and row['Average_Transaction_Amount'] <= 500000): val ='2. >250.000 - 500.000' elif (row['Average_Transaction_Amount'] >500000 and row['Average_Transaction_Amount'] <= 750000): val ='3. >500.000 - 750.000' elif (row['Average_Transaction_Amount'] >750000 and row['Average_Transaction_Amount'] <= 1000000): val ='4. >750.000 - 1.000.000' elif (row['Average_Transaction_Amount'] >1000000 and row['Average_Transaction_Amount'] <= 2500000): val ='5. >1.000.000 - 2.500.000' elif (row['Average_Transaction_Amount'] >2500000 and row['Average_Transaction_Amount'] <= 5000000): val ='6. >2.500.000 - 5.000.000' elif (row['Average_Transaction_Amount'] >5000000 and row['Average_Transaction_Amount'] <= 10000000): val ='7. >5.000.000 - 10.000.000' else: val ='8. >10.000.000' return val # Tambahkan kolom baru df['Average_Transaction_Amount_Group'] = df.apply(f, axis=1) df_year = df.groupby(['Average_Transaction_Amount_Group'])['Customer_ID'].count() df_year.plot(x='Average_Transaction_Amount_Group', y='Customer_ID',kind='bar', title='Customer Distribution by Average Transaction Amount Group') plt.xlabel('Average_Transaction_Amount_Group') plt.ylabel('Num_of_Customer') plt.tight_layout() plt.show()
И, как видно из графика, максимальное среднее значение транзакции находится в диапазоне 1 000 000–2 500 000 рупий.
МОДЕЛИРОВАНИЕ
Моделирование используется для прогнозирования оттока клиентов в ближайшем будущем. Эта модель использует логистическую регрессию, чтобы предсказать, сколько клиентов, которые прогнозировались, будут отброшены, клиентов. Первый шаг, мы можем решить, какая переменная будет использоваться для обучения данных. В качестве независимой переменной мы будем использовать столбец функций, который содержит Average_Transaction_Amount, Count_Transaction и Year_Diff. А для зависимой переменной мы будем использовать столбец «is_churn».
# Feature column: Year_Diff df['Year_Diff'] = df['Year_Last_Transaction'] - df['Year_First_Transaction'] feature_columns = ['Average_Transaction_Amount', 'Count_Transaction', 'Year_Diff'] # Features variable X = df[feature_columns] # Target variable y = df['is_churn']
После этого мы можем разделить набор данных для обучения и тестирования с соотношением 25%, которое будет использоваться в качестве данных тестирования для прогнозирования точности.
from sklearn.model_selection import train_test_split X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.25, random_state=0)
И мы можем применить модель LogisticRegression() из библиотеки sklearn, используя следующие команды:
from sklearn.linear_model import LogisticRegression from sklearn.metrics import confusion_matrix # Inisiasi logreg logreg = LogisticRegression() # fit the model with data logreg.fit(X_train, y_train) # Predict model y_pred = logreg.predict(X_test) # evaluate model using confusion matrix cnf_matrix = confusion_matrix(y_test, y_pred) print('Confusion Matrix:\n', cnf_matrix)
И теперь мы можем визуализировать матрицу путаницы
# import required modules import numpy as np import matplotlib.pyplot as plt import seaborn as sns plt.clf() # name of classes class_names = [0, 1] fig, ax = plt.subplots() tick_marks = np.arange(len(class_names)) plt.xticks(tick_marks, class_names) plt.yticks(tick_marks, class_names) # create heatmap sns.heatmap(pd.DataFrame(cnf_matrix), annot=True, cmap='YlGnBu', fmt='g') ax.xaxis.set_label_position('top') plt.title('Confusion matrix', y=1.1) plt.ylabel('Actual') plt.xlabel('Predicted') plt.tight_layout() plt.show()
Из графика видно, что существует 16666 клиентов, которые, по прогнозам, уйдут и будут уходить. И только 1 клиент, который, по прогнозам, не уйдет и будет отточен. Мы также можем подсчитать точность, точность и отзыв, используя команду ниже:
# Accuracy, Precision, dan Recall print('Accuracy :', accuracy_score(y_test,y_pred)) print('Precision:', precision_score(y_test, y_pred, average='micro')) print('Recall :', recall_score(y_test, y_pred, average='micro'))
Модель тестируется на 25% данных и дает значение точности 60%.