t-критерийA/B-тестстатистикаpythonscipy

t-критерий Стьюдента простыми словами и пример

2026-07-10 12 мин

Коротко: t-критерий Стьюдента проверяет, отличаются ли средние двух групп настолько, что случайностью это объяснить трудно. Он считает t-статистику — насколько разница средних велика в единицах шума (стандартной ошибки), — и переводит её в p-value. Маленькое p-value (обычно < 0.05) говорит: разница вряд ли случайна. В A/B-тестах чаще всего берут двухвыборочный тест Уэлча, потому что он не требует равенства дисперсий групп.

Что показывает t-критерий Стьюдента простыми словами?

Представь, что в A/B-тесте у контрольной группы средняя выручка на пользователя 512 рублей, а у тестовой — 548. Разница 36 рублей. Вопрос на миллион: это реальный эффект нового баннера или просто в тестовую группу случайно попало несколько крупных покупателей?

t-критерий отвечает на этот вопрос через одну идею: он сравнивает наблюдаемую разницу средних с тем, насколько сильно средние вообще скачут от выборки к выборке. Если разница в разы больше типичного разброса — эффект похож на настоящий. Если сопоставима с разбросом — это шум.

Формально t-статистика — это отношение сигнала к шуму:

t = (разница средних) / (стандартная ошибка этой разницы)

Чем больше по модулю t, тем сильнее сигнал выделяется на фоне шума. А p-value — вероятность увидеть такое (или ещё большее) t, если на самом деле разницы между группами нет. Логика та же, что за p-value простыми словами: мы не доказываем, что эффект есть, а показываем, что «ничего нет» плохо объясняет данные.

Важно, чего t-тест НЕ делает: он не говорит, что эффект большой или бизнес-значимый. Он говорит только о статистической значимости. Оценивать размер эффекта нужно отдельно — через доверительный интервал.

Одновыборочный, двухвыборочный, парный — когда какой?

Есть три разновидности, и путать их — классическая ошибка на собеседовании.

Тип тестаЧто сравниваемПример из аналитики
ОдновыборочныйСреднее одной группы с фиксированным числомСредний чек = 500 руб. по нормативу?
Двухвыборочный (независимый)Средние двух РАЗНЫХ группВыручка контроль vs тест в A/B
ПарныйДве измерения на ОДНИХ и тех же объектахКонверсия магазинов до и после редизайна

Главная ловушка: применить независимый тест там, где данные парные. Тогда ты выбрасываешь информацию о связи и теряешь мощность — рискуешь не заметить реальный эффект. И наоборот: парный тест на независимых группах вообще неприменим.

Как устроена формула t-статистики?

Разберём двухвыборочный случай, он самый частый. Обозначим средние групп как m1 и m2, дисперсии как s1² и s2², размеры как n1 и n2.

Классический тест Стьюдента (предполагает равные дисперсии) считает так:

t = (m1 - m2) / (Sp * sqrt(1/n1 + 1/n2))

где Sp — объединённое стандартное отклонение:
Sp = sqrt( ((n1-1)*s1^2 + (n2-1)*s2^2) / (n1 + n2 - 2) )

Тест Уэлча (не требует равных дисперсий) считает стандартную ошибку иначе:

t = (m1 - m2) / sqrt(s1^2/n1 + s2^2/n2)

Разберём знаменатель по частям, потому что в нём вся суть:

Дальше t сравнивают с t-распределением с определённым числом степеней свободы. У распределения Стьюдента хвосты толще, чем у нормального, — это плата за то, что дисперсию мы не знаем точно, а оцениваем по выборке. На больших n (сотни-тысячи наблюдений, как в типичном A/B) t-распределение почти совпадает с нормальным.

Число степеней свободы для теста Стьюдента = n1 + n2 - 2, а для Уэлча считается по громоздкой формуле Уэлча–Саттертуэйта и обычно получается дробным. Руками это не считают — за тебя всё сделает scipy.

Какие допущения у теста и что такое критерий Уэлча?

У t-критерия три допущения, и относиться к ним надо трезво.

Именно поэтому существует критерий Уэлча — модификация t-теста, которая НЕ предполагает равные дисперсии. Он считает стандартную ошибку по формуле выше и корректирует степени свободы. Практическое правило простое:

По умолчанию всегда используй тест Уэлча. Он почти не теряет мощности, когда дисперсии равны, и защищает тебя, когда они различаются. В scipy это флаг equal_var=False.

Отдельно про данные, где нормальность плохая даже после ЦПТ (например, доля-конверсия на малых выборках или сильно скошенная выручка с редкими выбросами): там лучше подойдут непараметрический тест Манна–Уитни, бутстрап или z-тест пропорций для конверсии. t-тест — не универсальный молоток.

Как посчитать t-тест в Python через scipy.stats.ttest_ind?

Самый частый инструмент — scipy.stats.ttest_ind. Сравним выручку двух групп A/B-теста. Сначала синтетические данные, чтобы код запускался как есть.

import numpy as np
from scipy import stats

rng = np.random.default_rng(42)

# Контроль и тест: выручка на пользователя, руб.
control = rng.normal(loc=512, scale=140, size=1800)
treatment = rng.normal(loc=548, scale=155, size=1820)

# Тест Уэлча (equal_var=False) — рекомендуемый вариант для A/B
t_stat, p_value = stats.ttest_ind(treatment, control, equal_var=False)

print(f"Среднее контроль:  {control.mean():.1f}")
print(f"Среднее тест:      {treatment.mean():.1f}")
print(f"Разница:           {treatment.mean() - control.mean():.1f}")
print(f"t-статистика:      {t_stat:.3f}")
print(f"p-value:           {p_value:.4f}")

Типичный вывод: разница около 35 рублей, t-статистика примерно 7, p-value заметно меньше 0.001. Вывод: разница статистически значима.

Для парного теста используется другая функция — ttest_rel (данные должны идти парами и быть одной длины):

before = np.array([120, 98, 145, 110, 132, 101])
after  = np.array([131, 105, 150, 121, 139, 115])

t_stat, p_value = stats.ttest_rel(after, before)
print(f"t = {t_stat:.3f}, p = {p_value:.4f}")

Для одновыборочногоttest_1samp, где второй аргумент это эталонное значение:

sla_hours = np.array([3.8, 4.2, 5.1, 3.9, 4.6, 4.0, 4.9])
t_stat, p_value = stats.ttest_1samp(sla_hours, popmean=4.0)
print(f"t = {t_stat:.3f}, p = {p_value:.4f}")

И почти обязательный спутник теста — доверительный интервал на разницу средних. p-value говорит «есть эффект или нет», а интервал показывает, насколько он большой:

diff = treatment.mean() - control.mean()
se = np.sqrt(treatment.var(ddof=1)/len(treatment) + control.var(ddof=1)/len(control))
ci_low, ci_high = diff - 1.96*se, diff + 1.96*se
print(f"Разница {diff:.1f} руб., 95% ДИ: [{ci_low:.1f}; {ci_high:.1f}]")

Хочешь прогнать эти сниппеты и поменять размеры выборок — открой Python-тренажёр, там scipy уже подключён и ничего ставить не надо. Если пробелов в pandas/numpy пока много, начни с курса pandas с нуля.

Как интерпретировать p-value в A/B-тесте?

Стандартный порог значимости alpha = 0.05. Логика решения:

Чего p-value НЕ означает (и что любят спрашивать на собесе):

Поэтому решение по A/B-тесту принимают по трём вещам сразу: p-value (значимо ли), доверительный интервал (насколько велик эффект и не задевает ли ноль) и заранее заданный минимальный детектируемый эффект. А размер выборки под нужную мощность считают ДО теста — иначе половина результатов окажется недоказуемой. Полезно освежить ошибки первого и второго рода и доверительный интервал.

Какие ошибки чаще всего делают с t-тестом?

Собрал грабли, на которые наступают чаще всего.

Разбор целого A/B-кейса с кодом есть в разборе тестового по A/B и в статье A/B-тесты на Python через scipy.stats.

Что спрашивают про t-критерий на собеседовании?

Подборка реальных формулировок с короткими ответами — чтобы не поплыть.

Разбор метрик, которые обычно и сравнивают t-тестом, лежит в карточках ARPU и среднего чека AOV. Больше теории для собеса — в подборке главных вопросов по статистике и в банке вопросов по интервью.

Понимать t-критерий по-настоящему получается, только когда сам считаешь t-статистику и p-value на живых данных, а не пересказываешь формулу. Собери всё вместе так: возьми пару выборок в Python-тренажёре, прогони ttest_ind с equal_var=False, построй доверительный интервал, а потом на том же датасете посчитай агрегаты в SQL-тренажёре. Первые пять задач открыты бесплатно, дальше — Pro. Если хочется прогнать эти вопросы вслух перед реальным собеседованием, есть AI мок-собес, который гоняет именно по статистике и A/B.

Держи в голове одну связку: t-критерий — это сигнал делить на шум, p-value — перевод этого сигнала в вероятность, а доверительный интервал — размер эффекта. Три числа вместе, а не одно из них, и есть грамотное решение по A/B-тесту.

Потренируй t-тест на живых данных
Первые 5 задач в Python-тренажёре открыты бесплатно: считаешь t-статистику и p-value на настоящих выборках, без установки окружения. Дальше — Pro.
Открыть Python-тренажёр →