Модуль 20. A/B-тесты и причинность¶
Чему вы научитесь в этом модуле
- Объяснять, почему корреляция не доказывает причину, и называть роль конфаундера.
- Описывать, что именно исправляет рандомизация и почему A/B-тест является причинным экспериментом.
- Показывать на симуляции, каким образом подглядывание в промежуточные результаты порождает ложную значимость.
- Объяснять, почему проверка двадцати метрик даёт «значимую» по построению, даже если реального эффекта нет.
- Собирать честный A/B-тест и перечислять ловушки, которые его портят, — те же самые, что в модуле 1.
Время: около двух недель. Пререквизиты: модуль 1 и модуль 19.
Ноутбук: открыть в Colab · notebooks/20-ab-tests-and-causality.ipynb
Зачем нужен этот модуль¶
Модули 18 и 19 упёрлись в один и тот же вопрос: как узнать, что новая версия рекомендателя действительно лучше, а не просто раскрутила петлю на удобных данных. Ответ — причинный эксперимент, и этот же метод закрывает всю часть о рекомендациях. Но приёмы, изложенные здесь, шире, чем рекомендательные системы: это общий способ отличить «X улучшил Y» от «X и Y просто ходят вместе».
Корреляция — не причина¶
«У кого включена новая лента, те проводят в приложении больше времени» — и хочется немедленно объявить, что новая лента удерживает лучше. Осторожно. Новую ленту могли раскатить сначала на активных пользователей; тогда разница объясняется не лентой, а тем, кому она досталась.
Скрытая переменная \(Z\) — «пользователь и так активен» — влияет и на воздействие \(X\) (кому раскатили ленту), и на исход \(Y\) (время в приложении). Именно \(Z\) создаёт корреляцию между \(X\) и \(Y\), а причинной стрелки от \(X\) к \(Y\) может вовсе не быть. Такая переменная называется конфаундером, и пока она присутствует, из наблюдения причину извлечь невозможно.
Рандомизация исправляет это¶
Единственный надёжный способ убрать конфаундер — не пытаться его измерить хитрее, а разорвать стрелку от него к воздействию. Назначайте, кому достанется новая лента, случайно — подбросом монеты, не глядя ни на активность, ни на что-либо ещё.
После случайного назначения группы A и B одинаковы во всём, кроме самого воздействия: активные пользователи, новички, полуночники — все распределены по обеим группам поровну. Следовательно, любую разницу в исходе можно списать только на воздействие, и ни на что другое. Это и есть A/B-тест — причинный эксперимент, а не наблюдение. Именно поэтому в модулях 18 и 19 честной проверкой рекомендателя назывался он, а не метрика на логах.
Подглядывание¶
Рандомизация — лишь половина честности. Вторая половина — как вы смотрите на результат. И здесь возвращаются ловушки из модуля 1, словно старые знакомые.
Соблазн велик: следить за тестом в реальном времени и остановить его, как только разница стала «значимой». Это подглядывание, и оно ломает статистику. Даже когда никакого настоящего эффекта нет, разница между группами гуляет случайным образом, и рано или поздно она случайно перескочит порог значимости. Если остановиться именно в этот момент — вы объявите победу, которой не существует.
В этой демонстрации A и B взяты из одного и того же распределения — истинного эффекта нет вовсе. Синяя линия — наблюдаемая разница, полоса — 95-процентный доверительный интервал. Жмите «новый прогон»: в части прогонов интервал по ходу случайно исключает ноль (красные точки). Тот, кто остановился бы на первой красной точке, объявил бы значимый эффект — на чистом шуме. Это «остановка по результату» из модуля 1, пункт пятый.
Защита та же самая: число наблюдений и момент проверки фиксируются заранее. Если хочется смотреть по ходу — существуют методы последовательного анализа, которые повышают порог значимости за каждое подглядывание. Но нельзя решать по данным, когда остановиться, и одновременно делать вид, что не решал.
Множественные сравнения¶
Второй способ выдумать значимость — проверить сразу много всего. Одну метрику новая лента не сдвинула — тогда давайте посмотрим двадцать: клики, время на сайте, возвраты, глубину прокрутки, повторные визиты… При двадцати проверках на уровне 0.05 одна ложная значимость ожидается по построению, даже если на самом деле ничего не изменилось.
Это шестой способ ошибиться из модуля 1. Защита — поправка на множественность (Бонферрони и более мягкие варианты) или откровенное признание: «мы проверили двадцать метрик, вот результаты по всем двадцати». Одна заранее назначенная главная метрика стоит двадцати, выбранных задним числом.
Модуль 1 вернулся целиком. Подглядывание — это «остановка по результату», двадцать метрик — «множественные сравнения», а разброс между пользователями — тот же шум, что между зёрнами. A/B-тест добавляет к арсеналу модуля 1 ровно одно новое слово — рандомизацию, — а остальное ровно то же: бутстрэп-интервалы, правило перекрытия и честность относительно того, сколько всего было проверено.
Практическая часть¶
Часть 1. Работа с ноутбуком¶
Откройте notebooks/20-ab-tests-and-causality.ipynb. Только numpy и matplotlib, вычисления занимают секунды.
Что содержится внутри:
- Корреляция против причины: конфаундер порождает связь, которой нет. Наблюдательная оценка эффекта смещена, рандомизированная — нет. Разница видна на числах.
- Подглядывание: A равно B, но остановка на первой значимости даёт ложных срабатываний в разы больше пяти процентов. Подсчитано, а не предположено.
- Множественные сравнения: двадцать честных метрик, одна «значимая» по построению. Поправка Бонферрони возвращает уровень ложных срабатываний на место.
Часть 2. Собственный эксперимент¶
Возьмите любое изменение, которое хотелось бы проверить: в продукте, в рассылке, в собственной привычке.
- Что здесь воздействие \(X\), что исход \(Y\), и какой конфаундер \(Z\) мог бы связать их без причинной стрелки?
- Как выглядело бы случайное назначение? Что мешает его сделать?
- Какую одну метрику вы назначите главной заранее?
- Сколько наблюдений соберёте до того, как посмотрите на результат?
Задание¶
- Сгенерируйте данные с конфаундером и покажите, что наблюдательная оценка эффекта смещена, а рандомизированная — нет.
- Смоделируйте подглядывание: A равно B, проверка после каждой сотни наблюдений, остановка на первой значимости. Измерьте долю ложных побед и сравните с фиксированным \(n\).
- Проверьте двадцать независимых метрик на данных без эффекта и посчитайте, как часто хотя бы одна из них оказывается «значимой». Сравните с поправкой Бонферрони.
- Постройте A/B-тест честно: фиксированный \(n\), заранее выбранная метрика, бутстрэп-интервал из модуля 1. Сформулируйте вывод по правилу перекрытия.
- Придумайте эффект новизны: воздействие даёт всплеск, который со временем угасает. Покажите, как короткий тест его переоценит.
Проверка усвоения¶
- Что такое конфаундер и почему из-за него корреляция не доказывает причину?
- Что именно исправляет рандомизация и почему после неё разница становится причинной?
- Почему подглядывание порождает ложную значимость, даже когда реального эффекта нет?
- Почему двадцать метрик дают «значимую» по построению?
- Какие три ловушки модуля 1 повторяются в A/B-тесте?
- Что защищает от подглядывания и от множественных сравнений?
- Почему метрика на логах не заменяет A/B-тест?
Что дальше¶
Часть V закончена: от коллаборативной фильтрации до причинного эксперимента, который единственный позволяет отличить улучшение от раскрученной петли. В части VI — агенты: цикл с инструментами и памятью, поиск с проверкой цитат, и оценка, где regression — это снова разница между прогонами, а eval — тот же тест из модуля 7.
A/B-тест — это причинный эксперимент: рандомизация разрывает конфаундер, и разница в исходе становится следствием воздействия. Но подглядывание и двадцать метрик ломают его точно так же, как ломали любое измерение в модуле 1.
Принцип
Рандомизация даёт право произнести слово «причина», но не отменяет честности в том, как вы смотрели на результат. Число наблюдений и главная метрика назначаются до эксперимента, а не выбираются по его результату.