pandasОбъединение таблицMediumБесплатно~7 мин

Anti-join: пользователи, которые ни разу не купили

// Условие

Есть две таблицы: df (все зарегистрированные юзеры) и orders (заказы). Не все юзеры делали заказы — именно их нужно найти.

Что нужно
Найди всех юзеров, которых нет в таблице orders — они зарегистрировались, но ни разу не купили. Это классический «churned without converting» — цель для реактивации.

Верни DataFrame с колонками user_id, signup_date, country, plan. Сортировка по signup_date asc.

Идиоматичный pandas-способ — left join с indicator=True, потом фильтр по 'left_only'. Есть и короткий альтернативный вариант через isin.

// Данные

df (users): user_id, signup_date, country, plan
orders: order_id, user_id, amount, order_date — доступна напрямую в namespace
▶ Решить в pandas-тренажёре

// Решение

Подсказка

Классический anti-join: df.merge(orders[['user_id']].drop_duplicates(), on='user_id', how='left', indicator=True). После merge у «непокупателей» в колонке _merge будет значение 'left_only'.

Отфильтруй: [merged['_merge'] == 'left_only']. Убери лишнюю колонку _merge через .drop(columns='_merge').

Альтернатива через isin — короче: df[~df['user_id'].isin(orders['user_id'])]. Оба способа дают одинаковый результат — знай оба.

Сначала попробуй сам → Показать решение
df = load_data()  # users
# orders уже в namespace

# Anti-join через indicator=True
merged = df.merge(
    orders[['user_id']].drop_duplicates(),
    on='user_id', how='left', indicator=True
)
result = (merged[merged['_merge'] == 'left_only']
          .drop(columns='_merge')
          .sort_values('signup_date')
          .reset_index(drop=True))

print(result)
print(f"\nНепокупателей: {len(result)} из {len(df)} юзеров")

Anti-join — pandas-аналог SQL LEFT JOIN ... WHERE right.key IS NULL. Два способа:
1) merge(indicator=True) + фильтр 'left_only' — явный, хорошо читается, удобен когда потом нужны колонки из правой таблицы;
2) df[~df['user_id'].isin(orders['user_id'])] — короче, но чуть медленнее на больших данных из-за построения множества.
На собесе спросят оба варианта и разницу в производительности. «Churned without converting» — один из главных сегментов для реактивационных кампаний: люди дошли до регистрации, но так и не купили.

// Похожие задачи