<jupyter_start><jupyter_text>1. Каково соотношение ушедших и лояльных клиентов? Покажите это на графике и дайте комментарий по соотношению.<jupyter_code>import plotly.graph_objects as go

exited_value_counts = churn_data['Exited'].value_counts().rename(index={0: 'лояльные', 1: 'ушедшие'})
exited_status = exited_value_counts.index
exited_counts = exited_value_counts.values

fig = go.Figure(data=[go.Pie(labels=exited_status, values=exited_counts)])
fig.update_layout(title_text='Соотношение ушедших и лояльных клиентов')
fig.show()<jupyter_output><empty_output><jupyter_text>В результате получили круговую диаграмму, из которой:1. видим, что количество ушедших клиентов в ~4 раза меньше, чем оставшихся;1. банку есть над чем работать)  2. Постройте график, показывающий распределение баланса пользователей, у которых на счету больше 2 500 долларов. Опишите распределение и сделайте выводы.<jupyter_code>import plotly.express as px
import numpy as np
from numerize import numerize

hist_data = churn_data[churn_data['Balance'] > 2500]
q25 = np.quantile(hist_data.Balance, 0.25)
q75 = np.quantile(hist_data.Balance, 0.75)
fig = px.histogram(
    data_frame=hist_data,
    x='Balance',
    title='Распределение баланса пользователей, у которых на счету больше $2500'
)
fig.add_vline(x=q25, line_dash = 'dash', line_color = 'firebrick', annotation_text=f'${numerize.numerize(q25)}')
fig.add_vline(x=q75, line_dash = 'dash', line_color = 'firebrick', annotation_text=f'${numerize.numerize(q75)}')
fig.show()<jupyter_output><empty_output><jupyter_text>В результате получили гистограмму, на которой видно, что:1. показатель баланса имеет [нормальное распределение](https://ru.wikipedia.org/wiki/Нормальное_распределение);1. 50% клиентов имеют баланс ~ 100-140k $.  3. Посмотрите на распределение баланса клиента в разрезе признака оттока. Как различаются суммы на накопительном счёте ушедших и лояльных клиентов? Подумайте и напишите, с чем это может быть связано, что может не устраивать ушедших клиентов в банке.<jupyter_code>fig = px.histogram(
    data_frame=churn_data,
    x='Balance',
    color='Exited',
    title='Распределение сумм на накопительных счетах ушедших и лояльных клиентов',
    labels={'Exited': 'Статус'}
)
fig.update_traces()
fig.for_each_trace(lambda t: t.update(name = {'1': 'Ушедшие', '0': 'Лояльные'}[t.name]))
fig.show()<jupyter_output><empty_output><jupyter_text>В результате, из графика можно сделать вывод, что1. тип распределения для ушедших и лояльных клиентов не отличается;1. значительно различаются суммы ушедших и лояльных клиентов, у лояльных клиентов сумма больше, тк их количество больше;1. количество лояльных клиентов с нулевым балансом значительно превышает количество ушедших с нулевым балансом. Возможно, в банке хорошие условия, а именно, не нужно платить за обслуживание карты.1. я считаю, по данному графику трудно сказать, что может не устраивать ушедших клиентов в банке. Причины могут быть разными, от смены места жительства до лучших условий в другом банке.    4. Посмотрите на распределение возраста в разрезе признака оттока. В какой группе больше потенциальных выбросов? На какую возрастную категорию клиентов стоит обратить внимание банку?<jupyter_code>fig = px.box(
    data_frame=churn_data,
    x='Age',
    color='Exited',
    labels={'Exited': 'Статус'},
    title='Распределение возраста клиентов в разрезе признака оттока'   
)
fig.for_each_trace(lambda t: t.update(name = {'1': 'Ушедшие', '0': 'Лояльные'}[t.name]))
fig.show()<jupyter_output><empty_output><jupyter_text>В результате, на графике видим, что больше потенциальных выбросов в группе лояльных клиентов, а обратить внимание следует на возрастную группу ~38-51, тк они составляют основную часть клиентов оттока.  5. Постройте график, который показывает взаимосвязь кредитного рейтинга клиента и его предполагаемой зарплаты. Добавьте расцветку по признаку оттока клиентов. Какова взаимосвязь между признаками? Если не видите явной взаимосвязи, укажите это.<jupyter_code>fig = px.scatter(
    data_frame=churn_data,
    y='CreditScore',
    x='EstimatedSalary',
    color='Exited',
    title='Взаимосвязь кредитного рейтинга клиента и его предполагаемой зарплаты'   
)
fig.show()<jupyter_output><empty_output><jupyter_text>В результате, по данному графику не удалсь установить зависимость.  6. Кто чаще уходит, мужчины или женщины? Постройте график, который иллюстрирует это.<jupyter_code>bar_data = churn_data.groupby(['Gender'], as_index=False).mean()
fig = px.bar(
    data_frame=bar_data,
    x='Gender',
    y='Exited',
    text_auto='.2%',
    title='Соотношение ушедших мужчин и женщин'
)
fig.show()<jupyter_output><empty_output><jupyter_text>В резутате, по графику видим, что чаще уходят женщины.  7.  Как отток клиентов зависит от числа приобретённых у банка услуг? Для ответа на этот вопрос постройте многоуровневую столбчатую диаграмму.<jupyter_code>bar_data = churn_data.groupby(['NumOfProducts', 'Exited'], as_index=False).count()
fig = px.bar(
    data_frame=bar_data,
    y='RowNumber',
    x='NumOfProducts',
    color='Exited',
    barmode='group',
    labels={'Exited': 'Отток'},
    text_auto=True,
    title='Соотношение ушедших и лояльных клиентов в зависимости от числа услуг'
)
fig.show()<jupyter_output><empty_output><jupyter_text>В результате, по диаграмме можно заметить, что, начиная со второй услуги, доля ушедших клиентов возрастает (в процентном соотношении). Но в абсолютном значении падает, т.е. чем меньше приобретено услуг, тем больше отток.  8. Как влияет наличие статуса активного клиента на отток клиентов? Постройте диаграмму, иллюстрирующую это. Что бы вы предложили банку, чтобы уменьшить отток клиентов среди неактивных?<jupyter_code>act_data = churn_data.groupby(['IsActiveMember', 'Exited'], as_index=False).count()
fig = px.bar(
    data_frame=act_data,
    y='RowNumber',
    x='IsActiveMember',
    color='Exited',
    barmode='group',
    labels={'Exited': 'Отток', 'IsActiveMember': 'Активность', 'RowNumber': 'Количество'},
    text_auto=True,
    title='Зависимость оттока клиентов от их активности'
)
fig.show()<jupyter_output><empty_output><jupyter_text>В результате наблюдаем, что среди активных клиентов отток меньше.Возможно, банку необходимо сделать акцию или какую-нибудь игру, кешбек на карту, чтобы увеличить активность клиентов.   9. В какой стране доля ушедших клиентов больше? Постройте тепловую картограмму, которая покажет это соотношение на карте мира. Предположите, с чем это может быть связано.<jupyter_code>choropleth_data = churn_data.groupby(['Geography'], as_index=False).mean()

fig = px.choropleth(
    data_frame=choropleth_data, 
    locations='Geography',
    locationmode ='country names', 
    color='Exited',
    hover_name='Geography',
    title='Отток клиентов на карте мира',
    color_continuous_scale=px.colors.sequential.Plasma
)
fig.show()<jupyter_output><empty_output><jupyter_text>В результате, на диаграмме видим данные по трем странам, самый большой отток в Германии. Возможно, данный банк не учитывает какие-то национальные особенности (поддержка клиентов, поддержка специфичных платежных систем, интуитивность пользовательского интерфейса) и не может конкурировать с местными банками.  10. Переведите числовой признак CreditScore в категориальный. Для этого воспользуйтесь функцией get_credit_score_cat(), которая приведена ниже. Примените её к столбцу CreditScore и создайте новый признак CreditScoreCat — категории кредитного рейтинга.1. Постройте сводную таблицу, строками которой являются категории кредитного рейтинга (CreditScoreCat), а столбцами — количество лет, в течение которых клиент пользуется услугами банка (Tenure). В ячейках сводной таблицы должно находиться среднее по признаку оттока (Exited) — доля ушедших пользователей.2. На основе полученной сводной таблицы постройте тепловую карту с аннотацией. Найдите на тепловой карте категории клиентов, которые уходят чаще всего.<jupyter_code>def get_credit_score_cat(credit_score):
    if credit_score >= 300 and credit_score < 500:
        return "Very_Poor"
    elif credit_score >= 500 and credit_score < 601:
        return "Poor"
    elif credit_score >= 601 and credit_score < 661:
        return "Fair"
    elif credit_score >= 661 and credit_score < 781:
        return "Good"
    elif credit_score >= 781 and credit_score < 851:
        return "Excellent"
    elif credit_score >= 851:
        return "Top"
    elif credit_score < 300:
        return "Deep"
    # better alternative to the code above
    # labels = ['Deep', 'Very_Poor', 'Poor', 'Fair', 'Good', 'Excellent', 'Top']
    # info = np.iinfo(np.int64)
    # idx = pd.IntervalIndex.from_breaks([info.min, 300, 500, 601, 661, 781, 851, info.max], closed='left')
    # return labels[idx.get_loc(credit_score)]

cs_data = churn_data[['CreditScore', 'Tenure', 'Exited']].copy()

cs_data['CreditScoreCat'] = cs_data['CreditScore'].apply(get_credit_score_cat)

cs_exit_data = cs_data.groupby(['CreditScoreCat', 'Tenure'])['Exited'].mean().unstack(0)
cs_exit_by_years_data = cs_exit_data.transpose()
cs_exit_by_years_data.head(cs_exit_by_years_data.size)

fig = px.imshow(cs_exit_by_years_data)
fig.show()<jupyter_output><empty_output>
{'fraction_non_alphanumeric': 0.09617271835132483, 'fraction_numerical': 0.013957038490895213, 'mean_word_length': 5.6900072939460244, 'pattern_counts': {'":': 0, '<': 47, '<?xml version=': 0, '>': 48, 'https://': 1, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'chain_length': '10', 'dir': 'jupyter-structured-clean-dedup', 'id': '610901', 'license': 'MIT', 'n_tokens_mistral': 3690, 'n_tokens_neox': 4131, 'n_words': 854, 'path': 'visual_project/test_churn.ipynb', 'repo_name': 'mashkam/sf-1-guess-numb', 'size': '9171'}