# A/B тестирование ###### tags: `Теория` ## Полезные ссылки * https://kokoc.com/blog/a-b-testirovanie-chto-eto-takoe-etapy-i-instrumenty/ - помимо сухой теории, приведены примеры сервисов для проведения А/В тестировании 7 золотых правил A/B-тестирования: ![](https://i.imgur.com/lhWwjQu.png) --- ## Теория ### Яндекс-практикум #### Планирование запуска **A/B-тестирование, или сплит-тестирование**, — техника проверки гипотез. Позволяет оценить, как изменение сервиса или продукта повлияет на пользователей. Проводится так: аудиторию делят на две группы — контрольную (A) и тестовую (В). Группа A видит начальный сервис, без изменений. Группа B получает новую версию, которую и нужно протестировать. Эксперимент длится фиксированное время. В ходе тестирования собираются данные о поведении пользователей в разных группах. Если ключевая метрика в тестовой группе выросла по сравнению с контрольной, новую функциональность внедряют. ![](https://i.imgur.com/ceYDld0.png) Прежде чем провести A/B-тест, часто делают проверку корректности — **A/A тест**. В нём пользователей делят на две контрольные группы, которые видят одинаковый сервис. Ключевая метрика у групп отличаться не должна: если она разная — ищите ошибку. #### Длительность A/B-теста С запуском новой функциональности меняется поведение пользователей. Обычно им нужно время, чтобы привыкнуть к нововведению. Когда это произошло, успешность эксперимента можно оценить уже наверняка. Чем больше объём данных, тем меньше вероятность ошибки при проверке статистических гипотез. У A/B-теста есть **проблема подглядывания**: общий результат искажается, если новые данные поступают в начале эксперимента. Каждый, даже небольшой фрагмент новых данных, велик относительно уже накопленных — статистическая значимость достигается за короткий срок. Это одно из проявлений закона больших чисел. Если наблюдений мало, их разброс больше. Если много, случайные выбросы успели друг друга компенсировать. Значит, если выборка слишком мала, различия увидеть легко. Для статистического теста это снижение *p-value* до значений, достаточно маленьких, чтобы отвергнуть нулевую гипотезу об отсутствии различий. Чтобы избежать проблемы подглядывания, размер выборки определяют ещё до начала теста. Вот правильная процедура A/B-тестирования: ![](https://i.imgur.com/Vm7LZcM.png) А так делать A/B-тестирование **не** стоит: ![](https://i.imgur.com/vg3fQrd.png) Простой способ найти размер выборки — рассчитать в онлайн-калькуляторе, например: https://vwo.com/tools/ab-test-duration-calculator/ #### Сравнение средних значений Научимся анализировать результаты А/В-теста: среднее значение метрики опишет поведение всех пользователей вместе. Результаты измерения и средние значения — случайные величины. Значит, в них могут быть *случайные* погрешности. Спрогнозировать их невозможно, а вот оценить получится методами статистики. Допустим, наша нулевая гипотеза **H₀** звучит так: «Новая функциональность не улучшает метрики». Тогда альтернативная гипотеза **H₁** такая: «Новая функциональность улучшает метрики». На этапе проверки гипотез возможны ошибки двух типов: 1) **Ошибка первого рода** — когда нулевая гипотеза верна, но она отклоняется (ложно-*положительный* результат; новую функциональность приняли, поэтому *положительный*); 2) **Ошибка второго рода** — когда нулевая гипотеза не верна, но принимается (ложно-отрицательный результат). ![](https://i.imgur.com/6C5Vaxz.png) Чтобы принять или отвергнуть нулевую гипотезу, вычислим знакомый вам уровень значимости — **p-value**. Он показывает вероятность ошибки первого рода. А об ошибке второго рода ничего не сообщает. Если значение *p-value* больше **порогового значения**, то нулевую гипотезу отвергать не стоит. Меньше — есть основание отказаться от нулевой гипотезы. Общепринятые пороговые значения — 5% и 1%. Но только от специалиста по Data Science зависит окончательное решение, какой порог считать достаточным. Средние значения сравнивают методами проверки односторонних гипотез. В нашем случае одностороннюю альтернативную гипотезу принимают, если проверяемое значение намного больше принятого в нулевой гипотезе. Если распределение данных близко к нормальному (в данных нет существенных выбросов), для сравнения средних значения используют стандартный *t*-тест. Этот метод предполагает нормальное распределение средних из всех выборок и определяет, достаточно ли велика разница между сравниваемыми значениями, чтобы отклонить нулевую гипотезу об их равенстве. #### Доверительный интервал **Доверительный интервал** (*confidence interval*) — отрезок числовой оси, в который с заданной вероятностью попадает нужный нам параметр генеральной совокупности. Параметр неизвестен, но его можно оценить по выборке. Если величина с вероятностью 99% попадает в интервал от 300 до 500, то 99%-й доверительный интервал для неё — это **(300, 500)**. При вычислении доверительного интервала с каждой из его сторон обычно выбрасывают одинаковую долю экстремальных значений. Доверительный интервал — это не просто диапазон значений случайной величины. Величина, которую мы оцениваем, изначально неслучайная. Вероятность возникает потому, что число неизвестно и оценивается по выборке. Случайность выборки вносит случайность и в оценку. Доверительный интервал оценивает уверенность в этой оценке. ![](https://i.imgur.com/YceFzyV.png) #### Бутстреп для анализа A/B-теста *Bootstrap* применяют и в анализе результатов A/B-теста. Пока проводили тест, мы получали данные о показателях в контрольной и экспериментальной группах. Считаем *фактическую разницу целевых показателей* в группах. Затем формулируем и проверяем гипотезы. Нулевая предполагает равенство целевых показателей в обеих группах. Альтернативная — в экспериментальной группе целевой показатель выше. Найдём *p-value*. Вычислим разницу целевого показателя по выборкам. Найдём вероятность того, что такую разницу получили случайно (это и будет *p-value*). Объединим выборки. Бутстрепом получим распределение среднего чека. Создадим много подвыборок, каждую из которых с номером *i* разделим пополам: ![](https://i.imgur.com/n00fwYv.png) ![](https://i.imgur.com/cDuHFSx.png) Найдём между ними разницу целевого показателя: Оценим долю разниц целевых показателей в бутстрепе, которые оказались не меньше, чем разницы целевых показателей между исходными выборками: ![](https://i.imgur.com/1bAMgrJ.png) ``` python import pandas as pd import numpy as np # фактическая разность средних значений в группах AB_difference = samples_B.mean() - samples_A.mean() alpha = 0.05 state = np.random.RandomState(12345) bootstrap_samples = 1000 count = 0 for i in range(bootstrap_samples): # подсчитываем, сколько раз разница целевых показателей # фактическое значение при условии верности нулевой гипотезы united_samples = pd.concat([samples_A, samples_B]) subsample = united_samples.sample(frac=1, replace=True, random_state=state) subsample_A = subsample[:len(samples_A)] subsample_B = subsample[len(samples_A):] bootstrap_difference = subsample_B.mean() - subsample_A.mean() if bootstrap_difference >= AB_difference: count += 1 pvalue = 1. * count / bootstrap_samples print('p-value =', pvalue) if pvalue < alpha: print("Отвергаем нулевую гипотезу: скорее всего, целевой показатель увеличился") else: print("Не получилось отвергнуть нулевую гипотезу: скорее всего, целевой показатель не увеличился") ``` ### FAQ --- ## Идеи для типового проекта > заметки на основании теории, которые могут влиять на развитие описания типового проекта