假设检验基础

用数据验证统计假设

主题: 假设检验核心原理与Python实践

核心内容: 原假设与备择假设、显著性水平、p值解读、两类错误、正态性检验、方差齐性检验、置信区间、效应量、scipy.stats检验函数

关键词: 假设检验, p值, 显著性水平, 正态性检验, scipy.stats, 置信区间, 效应量

一、假设检验基本概念

假设检验(Hypothesis Testing)是统计推断的核心工具之一,它通过样本数据对总体参数或分布形式做出判断。其基本思想是:先对总体提出一个假设,然后利用样本数据去检验这个假设是否合理

1.1 原假设与备择假设

每个假设检验问题都包含两个对立假设:

假设检验的三种形式

以检验总体均值 μ 为例:

  • 双侧检验: H₀: μ = μ₀   vs   H₁: μ ≠ μ₀
  • 左侧单侧检验: H₀: μ ≥ μ₀   vs   H₁: μ < μ₀
  • 右侧单侧检验: H₀: μ ≤ μ₀   vs   H₁: μ > μ₀

1.2 显著性水平 α

显著性水平(Significance Level, α)是拒绝原假设时所能承受的最大风险概率,通常取值为 0.05(5%)或 0.01(1%)。其含义是:当原假设为真时,我们错误地拒绝它的概率不超过 α。

α 的选取原则:

  • 在医学、药物研发等高风险领域,通常取 α = 0.01 甚至 0.001
  • 在社会科学等探索性研究中,常取 α = 0.05
  • 在大规模数据筛查场景下,可使用 α = 0.1 以提高灵敏度

1.3 检验统计量

检验统计量(Test Statistic)是根据样本数据计算出的数值,用于判断是否拒绝原假设。常见的检验统计量包括:

t 检验统计量公式:

t = (x̄ - μ₀) / (s / √n)

其中 x̄ 为样本均值,μ₀ 为原假设均值,s 为样本标准差,n 为样本量

# Python 实现单样本 t 检验 import numpy as np from scipy import stats # 生成样本数据 np.random.seed(42) sample = np.random.normal(loc=102, scale=5, size=30) # 单样本 t 检验:检验均值是否等于 100 t_stat, p_value = stats.ttest_1samp(sample, popmean=100) print(f"t 统计量: {t_stat:.4f}") print(f"p 值: {p_value:.6f}") # 判断是否拒绝原假设 alpha = 0.05 if p_value < alpha: print("拒绝原假设:均值显著不等于 100") else: print("无法拒绝原假设:均值与 100 无显著差异")

二、两类错误与统计功效

2.1 Type I 错误(假阳性)

第一类错误(Type I Error): 原假设实际上为真,但被错误地拒绝了。这相当于"假阳性"—— 误报了一个不存在的效应。犯第一类错误的概率就是显著性水平 α

典型案例:

一种新药实际并无疗效(H₀ 为真),但临床试验结果却显示有效(拒绝了 H₀),这就是 Type I 错误。这正是为什么医学研究要求 α = 0.05 甚至更小——宁可漏过真效应,也不误报假效应。

2.2 Type II 错误(假阴性)

第二类错误(Type II Error): 原假设实际上为假,但未能被拒绝。这相当于"假阴性"—— 遗漏了一个真实存在的效应。犯第二类错误的概率记为 β

两类错误的关系:

  • 在样本量固定时,α 和 β 呈反向关系:降低 α 会增大 β,反之亦然
  • 唯一同时降低两类错误的方法:增加样本量
  • 在实际应用中,Type I 错误通常被认为比 Type II 错误更严重

2.3 统计功效(Power)

统计功效(Statistical Power) 定义为当备择假设为真时,正确拒绝原假设的概率,即 Power = 1 - β。统计功效反映了检验发现真实效应的能力。

影响统计功效的因素

  • 效应量(Effect Size): 真实效应越大,越容易被检测到,功效越高
  • 样本量(Sample Size): n 越大,功效越高
  • 显著性水平 α: α 越大,功效越高(但代价是 Type I 错误增加)
  • 变异程度: 数据变异越小,功效越高
# 使用 statsmodels 进行功效分析 from statsmodels.stats.power import TTestIndPower # 指定参数计算所需样本量 effect_size = 0.5 # Cohen's d = 0.5(中等效应) alpha = 0.05 # 显著性水平 power = 0.80 # 目标功效 analysis = TTestIndPower() n = analysis.solve_power( effect_size=effect_size, alpha=alpha, power=power, alternative='two-sided' ) print(f"所需样本量: {np.ceil(n):.0f}") # 绘制功效曲线 import matplotlib.pyplot as plt fig = analysis.plot_power( dep_var='nobs', nobs=np.arange(10, 500), effect_size=[0.2, 0.5, 0.8], alpha=0.05 ) plt.title('统计功效与样本量关系曲线')
效应量 (Cohen's d) 小样本 (n=30) 中样本 (n=100) 大样本 (n=500)
小 (0.2) 0.14 0.29 0.80
中 (0.5) 0.48 0.88 0.99
大 (0.8) 0.81 0.99 1.00
注:表中数值为独立样本 t 检验在 α=0.05 双侧检验下的统计功效

Power Analysis 的应用场景:

  • 实验设计阶段: 在研究开始前计算所需的最小样本量
  • 研究预算规划: 权衡成本与统计功效,确定可行样本量
  • 已发表研究评估: 评估已有研究的检验能力,判断阴性结果是否可信

三、p 值深度解读

3.1 p < 0.05 的真正含义

p 值是在原假设为真的前提下,观察到当前结果(或更极端结果)的概率。p < 0.05 意味着:如果原假设为真,那么出现当前观测数据的概率不到 5%。

常见的 p 值误读(请务必避免):

  • 错误: p = 0.03 意味着原假设为假的概率是 97%
    正确: p = 0.03 意味着在原假设为真的条件下,观测到当前结果的概率为 3%
  • 错误: p = 0.03 意味着结果有 97% 的概率可重复
    正确: p 值不衡量结果的可重复性
  • 错误: p = 0.06 意味着两个组"没有差异"
    正确: p = 0.06 意味着在 α = 0.05 水平上无法拒绝原假设,但不等于两组相同

3.2 p 值不是效应概率

这是最常见的误解之一。p 值衡量的是 数据相对于原假设的极端程度,而不是效应为真的概率。要计算效应为真的后验概率,需要使用贝叶斯方法。p 值也无法告诉我们效应量的大小——一个非常大的样本中,即使微不足道的差异也可能产生极小的 p 值。

"p 值是数据与原假设不一致程度的度量,而不是效应存在的概率。一个很小的 p 值可能来自一个很大的样本量和一个很小的效应,而非一个很大的效应。" —— 美国统计学会(ASA)关于 p 值的声明,2016

3.3 p-hacking 与多重比较问题

p-hacking(p 值操纵) 指研究者通过多种数据分析和选择性报告的方式,人为获得显著 p 值的行为。常见形式包括:

多重比较校正方法

当同时进行多个假设检验时,需要校正显著性水平以控制整体 Type I 错误率:

  • Bonferroni 校正: 将 α 除以比较次数 m,即 α' = α / m。最保守,控制 Family-wise Error Rate (FWER)
  • Benjamini-Hochberg 校正(FDR): 控制错误发现率(False Discovery Rate),比 Bonferroni 更宽松,在探索性分析中更常用
  • Holm-Bonferroni 校正: 逐步降序法,比标准 Bonferroni 略温和
# p 值校正示例 from scipy.stats import false_discovery_control import numpy as np # 假设进行了 10 次检验,得到如下 p 值 p_values = np.array([0.001, 0.02, 0.03, 0.05, 0.10, 0.15, 0.25, 0.40, 0.60, 0.80]) # Bonferroni 校正 m = len(p_values) bonferroni_cutoff = 0.05 / m print(f"Bonferroni 校正阈值: {bonferroni_cutoff:.6f}") print(f"Bonferroni 显著: {p_values < bonferroni_cutoff}") # FDR 校正 (Benjamini-Hochberg) reject, p_corrected, _, _ = false_discovery_control(p_values) print(f"FDR 校正后显著的 p 值: {p_values[reject]}")

四、正态性检验

许多统计检验(如 t 检验、ANOVA)假设数据服从正态分布。正态性检验用于评估这一假设是否成立。以下介绍四种常用的正态性检验方法。

4.1 Shapiro-Wilk 检验

Shapiro-Wilk 检验是最常用的正态性检验之一,尤其适用于 小样本(n < 5000) 的情况。它基于顺序统计量的比值计算检验统计量 W,W 越接近 1 说明数据越接近正态分布。

# Shapiro-Wilk 正态性检验 from scipy.stats import shapiro # 生成正态分布数据 np.random.seed(42) normal_data = np.random.normal(loc=0, scale=1, size=100) stat_w, p_shapiro = shapiro(normal_data) print(f"Shapiro-Wilk W 统计量: {stat_w:.4f}") print(f"p 值: {p_shapiro:.4f}") print("结论: 数据服从正态分布" if p_shapiro > 0.05 else "结论: 数据不服从正态分布")

4.2 D'Agostino K² 检验

D'Agostino K² 检验基于数据的 偏度(Skewness)峰度(Kurtosis) 联合检验正态性。它计算一个综合的 K² 统计量,在大样本下近似服从 χ² 分布。

# D'Agostino K² 检验 from scipy.stats import normaltest stat_k2, p_k2 = normaltest(normal_data) print(f"D'Agostino K² 统计量: {stat_k2:.4f}") print(f"p 值: {p_k2:.4f}") # 检查偏度和峰度 from scipy.stats import skew, kurtosis print(f"偏度: {skew(normal_data):.4f}") print(f"峰度: {kurtosis(normal_data):.4f}")

4.3 Anderson-Darling 检验

Anderson-Darling 检验是 EDF(经验分布函数)检验的一种,对分布的尾部差异特别敏感。它不仅可以检验正态性,还可以检验其他分布(如指数分布、极值分布等)。

# Anderson-Darling 检验 from scipy.stats import anderson result = anderson(normal_data, dist='norm') print(f"AD 统计量: {result.statistic:.4f}") print("临界值:") for cv, sl in zip(result.critical_values, result.significance_level): print(f" 显著性水平 {sl}%: {cv:.4f}") print(f"结论: {'数据服从正态分布' if result.statistic < result.critical_values[2] else '数据不服从正态分布'}")

4.4 Q-Q 图(可视化方法)

Q-Q 图(Quantile-Quantile Plot)通过比较数据的分位数与理论正态分布的分位数来直观判断正态性。如果数据点大致落在参考线上,则数据接近正态分布。

# Q-Q 图绘制 import matplotlib.pyplot as plt import scipy.stats as stats fig, axes = plt.subplots(1, 2, figsize=(12, 5)) # 正态数据 stats.probplot(normal_data, dist="norm", plot=axes[0]) axes[0].set_title("正态数据的 Q-Q 图") # 偏态数据对比 skewed_data = np.random.exponential(scale=2, size=100) stats.probplot(skewed_data, dist="norm", plot=axes[1]) axes[1].set_title("偏态数据的 Q-Q 图") plt.tight_layout() plt.show()
方法 适用场景 优点 缺点
Shapiro-Wilk n < 5000 检验效力高,公认的黄金标准 大样本时计算量大,过于敏感
D'Agostino K² n ≥ 20 可解析偏度和峰度的具体偏差 对尾部偏差不敏感
Anderson-Darling n ≥ 5 对尾部差异敏感,支持多种分布 临界值需查表,需要指定分布
Q-Q 图 任意样本量 直观可视,可发现异常模式 主观判断,不如数值检验精确

正态性检验注意事项:

  • 大样本陷阱: 当 n 很大时(如 > 5000),即使数据非常接近正态分布,正态性检验也可能拒绝 H₀。此时应结合 Q-Q 图综合判断。
  • 小样本局限: 当 n 很小时(如 < 10),正态性检验的效力不足,难以检测出偏离。此时应依赖领域知识判断。
  • 中心极限定理: 对于 t 检验等均值比较方法,当样本量足够大(n ≥ 30)时,即使数据轻微偏离正态分布,结果仍然稳健。

五、方差齐性检验

方差齐性(Homogeneity of Variance)是指多个组的总体方差相等。许多统计方法(如独立样本 t 检验、ANOVA)要求各组方差齐性。

5.1 Levene 检验

Levene 检验对数据分布的正态性假设不敏感,是最稳健的方差齐性检验方法。它使用各组数据与其组中位数的绝对离差进行 ANOVA。

# Levene 方差齐性检验 from scipy.stats import levene # 生成三组数据 group1 = np.random.normal(loc=0, scale=1, size=50) group2 = np.random.normal(loc=2, scale=1, size=50) group3 = np.random.normal(loc=1, scale=2, size=50) # 方差不同 stat_l, p_l = levene(group1, group2, group3) print(f"Levene 统计量: {stat_l:.4f}") print(f"p 值: {p_l:.4f}") print("结论: 各组方差齐性" if p_l > 0.05 else "结论: 各组方差不齐")

5.2 Bartlett 检验

Bartlett 检验基于各组方差的加权算术平均和几何平均之比构造检验统计量。它 对正态性假设非常敏感——如果数据偏离正态分布,Bartlett 检验的结果可能不可靠。

# Bartlett 检验(要求数据正态) from scipy.stats import bartlett stat_b, p_b = bartlett(group1, group2, group3) print(f"Bartlett 统计量: {stat_b:.4f}") print(f"p 值: {p_b:.4f}")

5.3 Fligner-Killeen 检验

Fligner-Killeen 检验是一种非参数的方差齐性检验方法,基于各组数据相对于中位数的绝对偏离进行秩变换。它不要求数据正态分布,且对异常值比较稳健。

# Fligner-Killeen 检验(非参数方法) from scipy.stats import fligner stat_fk, p_fk = fligner(group1, group2, group3) print(f"Fligner-Killeen 统计量: {stat_fk:.4f}") print(f"p 值: {p_fk:.4f}")
检验方法 是否需要正态性 稳健性 适用场景
Levene 检验 不需要 高(最稳健) 通用首选,特别是数据非正态时
Bartlett 检验 需要 低(对偏离敏感) 仅当数据确认正态分布时
Fligner-Killeen 检验 不需要 中等 数据非正态且有异常值时

六、置信区间

置信区间(Confidence Interval)给出了参数估计的一个区间范围,反映了估计的不确定性。95% 置信区间的含义是:如果重复抽样 100 次并计算 100 个置信区间,大约有 95 个区间包含真实的总体参数。

6.1 均值的置信区间

当总体方差未知时,均值的置信区间基于 t 分布计算:

均值 95% 置信区间:

CI = x̄ ± t_{α/2, n-1} × (s / √n)

其中 t_{α/2, n-1} 为自由度为 n-1 的 t 分布临界值

# 手动计算均值置信区间 from scipy.stats import t data = np.random.normal(loc=100, scale=15, size=50) n = len(data) mean = np.mean(data) se = stats.sem(data) # 标准误 alpha = 0.05 t_crit = t.ppf(1 - alpha/2, df=n-1) ci_lower = mean - t_crit * se ci_upper = mean + t_crit * se print(f"样本均值: {mean:.2f}") print(f"95% 置信区间: ({ci_lower:.2f}, {ci_upper:.2f})") # 使用 scipy 直接计算 ci = stats.t.interval(0.95, df=n-1, loc=mean, scale=se) print(f"验证: ({ci[0]:.2f}, {ci[1]:.2f})")

6.2 Bootstrap 自助法

Bootstrap 是一种基于重采样(resampling)的非参数统计方法,适用于难以用公式推导置信区间的情况。它通过对原始数据进行有放回抽样,模拟抽样分布,计算经验置信区间。

Bootstrap 置信区间计算步骤

  1. 从原始样本中 有放回 抽取 n 个观测值,形成 Bootstrap 样本
  2. 计算该 Bootstrap 样本的目标统计量(如均值、中位数)
  3. 重复步骤 1-2 共 B 次(通常 B ≥ 1000),得到 B 个 Bootstrap 统计量
  4. 取 Bootstrap 分布的 α/2 和 1-α/2 分位数作为置信区间上下限
# Bootstrap 置信区间(以中位数为例) np.random.seed(42) data = np.random.exponential(scale=3, size=100) # 偏态数据 B = 10000 bootstrap_stats = np.zeros(B) for i in range(B): boot_sample = np.random.choice(data, size=len(data), replace=True) bootstrap_stats[i] = np.median(boot_sample) ci_lower = np.percentile(bootstrap_stats, 2.5) ci_upper = np.percentile(bootstrap_stats, 97.5) print(f"样本中位数: {np.median(data):.2f}") print(f"Bootstrap 95% 置信区间: ({ci_lower:.2f}, {ci_upper:.2f})") # 使用 scipy 内置 bootstrap 函数 from scipy.stats import bootstrap res = bootstrap((data,), np.median, n_resamples=9999, confidence_level=0.95) print(f"scipy 结果: ({res.confidence_interval.low:.2f}, {res.confidence_interval.high:.2f})")

Bootstrap 的优缺点:

  • 优点: 无需假设数据分布形态、适用于复杂统计量(中位数、相关系数等)、实现简单
  • 缺点: 计算量大(需重复抽样数千次)、对原始样本的代表性有依赖、极端小样本效果不佳

七、效应量

p 值告诉我们差异是否"统计显著",但无法告诉我们差异是否"实际重要"。效应量(Effect Size)衡量的是效应的大小,帮助我们判断结果的实际意义。

7.1 Cohen's d

Cohen's d 是最常用的效应量指标之一,衡量两组均值之间的标准化差异。它不受样本量的影响,使得不同研究之间的效应可以相互比较。

Cohen's d 计算公式:

d = (x̄₁ - x̄₂) / s_p

其中 s_p 为合并标准差(pooled standard deviation)

s_p = √[((n₁-1)s₁² + (n₂-1)s₂²) / (n₁ + n₂ - 2)]

# 手动计算 Cohen's d def cohens_d(group1, group2): n1, n2 = len(group1), len(group2) s1, s2 = np.var(group1, ddof=1), np.var(group2, ddof=1) # 合并标准差 s_pooled = np.sqrt(((n1-1)*s1 + (n2-1)*s2) / (n1 + n2 - 2)) # Cohen's d d = (np.mean(group1) - np.mean(group2)) / s_pooled return d group_a = np.random.normal(loc=100, scale=15, size=50) group_b = np.random.normal(loc=108, scale=15, size=50) d = cohens_d(group_a, group_b) print(f"Cohen's d = {d:.3f}") # 解释效应量(Cohen 标准) if abs(d) < 0.2: print("效应量: 极小 (trivial)") elif abs(d) < 0.5: print("效应量: 小 (small)") elif abs(d) < 0.8: print("效应量: 中 (medium)") else: print("效应量: 大 (large)")

7.2 Eta-squared (η²)

Eta-squared 用于 ANOVA(方差分析),衡量自变量对因变量变异的解释比例。η² 的取值范围为 [0, 1],值越大表示自变量的效应越强。

Eta-squared 公式:

η² = SS_between / SS_total

其中 SS_between 为组间平方和,SS_total 为总平方和

# 计算 Eta-squared from scipy.stats import f_oneway k1 = np.random.normal(loc=50, scale=10, size=30) k2 = np.random.normal(loc=55, scale=10, size=30) k3 = np.random.normal(loc=60, scale=10, size=30) # ANOVA f_stat, p_anova = f_oneway(k1, k2, k3) # 计算 eta-squared all_data = np.concatenate([k1, k2, k3]) grand_mean = np.mean(all_data) group_means = [np.mean(g) for g in (k1, k2, k3)] group_sizes = [len(g) for g in (k1, k2, k3)] ss_between = sum(n * (m - grand_mean)**2 for n, m in zip(group_sizes, group_means)) ss_total = sum((x - grand_mean)**2 for x in all_data) eta_sq = ss_between / ss_total print(f"η² = {eta_sq:.4f}") print(f"F 统计量: {f_stat:.3f}, p 值: {p_anova:.5f}")

7.3 实际显著性 vs 统计显著性

这是数据分析中最容易被忽视的区别之一:

重要区分:

统计显著性(Statistical Significance): p < 0.05,表示观察到的效应不太可能由随机误差引起。但这仅说明效应存在,并不说明效应有多大或多重要。

实际显著性(Practical Significance): 效应量大到足以在实际应用中产生有意义的影响。一个统计显著的微小差异可能在实际中毫无价值。

典型案例:

假设某减肥药临床试验中,实验组比对照组平均多减重 0.3 公斤。在 10000 人的大样本下,这一差异完全可能达到统计显著(p < 0.001),但 0.3 公斤的减重效果在实际临床中几乎没有意义——这并不是一个有实际价值的减肥效果。

因此,报告结果时应当始终同时汇报 p 值和效应量,让读者能全面评估结果的意义。

指标 回答的问题 受样本量影响
p 值 效应是否存在(是否显著) 是(大样本更容易显著)
效应量 效应有多大(是否重要) 否(理论上不依赖样本量)
置信区间 效应的估计范围有多精确 是(大样本区间更窄)

八、scipy.stats 检验函数总结

scipy.stats 提供了丰富的假设检验函数,以下是对常用函数的系统总结:

8.1 均值比较检验

函数 用途 前提假设 语法要点
ttest_1samp 单样本 t 检验(均值 vs 常数) 数据正态分布 ttest_1samp(a, popmean)
ttest_ind 独立样本 t 检验(两组均值比较) 正态分布、方差齐性 ttest_ind(a, b, equal_var=True)
ttest_rel 配对样本 t 检验(前后比较) 差值正态分布 ttest_rel(a, b)
mannwhitneyu Mann-Whitney U 检验(非参数独立样本) 无分布假设 mannwhitneyu(x, y, alternative='two-sided')
wilcoxon Wilcoxon 符号秩检验(非参数配对样本) 差值对称分布 wilcoxon(x, y)

8.2 方差分析

函数 用途 前提假设 语法要点
f_oneway 单因素方差分析(三组及以上均值比较) 正态分布、方差齐性 f_oneway(*groups)
kruskal Kruskal-Wallis H 检验(非参数 ANOVA) 无分布假设 kruskal(*groups)

8.3 相关性检验

函数 用途 前提假设 语法要点
pearsonr Pearson 相关系数(线性相关) 双变量正态分布 pearsonr(x, y) 返回 (r, p)
spearmanr Spearman 秩相关系数(单调相关) 无分布假设 spearmanr(a, b)
kendalltau Kendall Tau 相关系数(有序数据) 无分布假设 kendalltau(x, y)
chi2_contingency 卡方检验(分类变量独立性) 期望频数 ≥ 5 chi2_contingency(observed)

8.4 正态性与分布检验

函数 用途 语法要点
shapiro Shapiro-Wilk 正态性检验 shapiro(x) 返回 (W, p)
normaltest D'Agostino K² 正态性检验 normaltest(x) 返回 (K², p)
anderson Anderson-Darling 正态性检验 anderson(x, dist='norm') 返回 (stat, critical_values)
ks_1samp Kolmogorov-Smirnov 单样本检验 ks_1samp(x, cdf)

8.5 方差齐性检验

函数 用途 语法要点
levene Levene 方差齐性检验(推荐首选) levene(*samples) 返回 (stat, p)
bartlett Bartlett 方差齐性检验(需正态) bartlett(*samples) 返回 (stat, p)
fligner Fligner-Killeen 方差齐性检验(非参数) fligner(*samples) 返回 (stat, p)

检验选择决策指南:

  • 步骤一: 用 Shapiro-Wilk 检验数据是否正态 → 是则用参数检验,否则用非参数检验
  • 步骤二(参数检验): 用 Levene 检验方差是否齐性 ← 是则用标准方法,否则用 Welch's t 检验(ttest_ind(equal_var=False)
  • 步骤三: 选择正确的效应量指标报告,同时评估统计显著性和实际显著性
# scipy.stats 假设检验完整流程示例 from scipy import stats import numpy as np np.random.seed(42) control = np.random.normal(loc=100, scale=15, size=40) treatment = np.random.normal(loc=110, scale=15, size=40) # 1. 正态性检验 _, p1 = stats.shapiro(control) _, p2 = stats.shapiro(treatment) print(f"正态性检验: control p={p1:.4f}, treatment p={p2:.4f}") # 2. 方差齐性检验 _, p_var = stats.levene(control, treatment) print(f"方差齐性 Levene 检验: p={p_var:.4f}") # 3. 选择适当的 t 检验 equal_var = p_var > 0.05 t_stat, p_value = stats.ttest_ind(control, treatment, equal_var=equal_var) print(f"独立样本 t 检验: t={t_stat:.3f}, p={p_value:.5f}") # 4. 效应量 n1, n2 = len(control), len(treatment) s1, s2 = np.var(control, ddof=1), np.var(treatment, ddof=1) s_p = np.sqrt(((n1-1)*s1 + (n2-1)*s2) / (n1 + n2 - 2)) d = (np.mean(treatment) - np.mean(control)) / s_p print(f"效应量 Cohen's d = {d:.3f}") # 5. 置信区间 se = s_p * np.sqrt(1/n1 + 1/n2) t_crit = stats.t.ppf(0.975, df=n1+n2-2) diff = np.mean(treatment) - np.mean(control) print(f"均值差 95% CI: ({diff - t_crit*se:.2f}, {diff + t_crit*se:.2f})")

九、常见误区与最佳实践

9.1 统计显著 ≠ 实际重要

如前所述,大样本可以使微小差异达到统计显著。始终报告效应量和置信区间,帮助读者理解结果的实际意义。

9.2 不显著 ≠ 无效应

p > 0.05 不代表原假设为真,只说明没有足够的证据拒绝原假设。可能的原因包括:样本量不足、效应量太小、数据变异太大或测量误差较大。

9.3 避免"p 值崇拜"

不要以 p < 0.05 作为判断结果价值的唯一标准。美国统计协会(ASA)2016 年的声明明确警告 p 值的误用和滥用,强调应该结合效应量、置信区间和研究设计综合判断。

假设检验最佳实践清单

  1. 在研究设计阶段进行 Power Analysis 确定样本量
  2. 预先确定显著性水平 α,不要在收集数据后再选
  3. 同时报告 p 值、效应量和置信区间
  4. 使用 Q-Q 图和正态性检验 验证前提假设
  5. 必要时进行 多重比较校正
  6. 考虑 Bootstrap 等非参数方法 作为补充分析
  7. 在探索性研究和验证性研究之间 明确区分
  8. 公开分析代码和数据,确保结果 可复现

十、核心要点总结