在数据分析和科学研究中,假设检验是一个非常重要的统计工具。本文将详细介绍两种常用的非参数检验方法:Mann-Whitney U检验(也称为Wilcoxon秩和检验)和卡方检验(Chi-square test),并使用Python来实现这些检验方法。
目录
-
-
-
-
基础概念
什么是假设检验?
假设检验是一种统计推断方法,用于判断样本数据是否支持某个统计假设。在进行假设检验时,我们通常会设置:
-
-
-
显著性水平(α):通常设为0.05,表示我们容忍的犯第一类错误的概率
为什么需要非参数检验?
当数据不满足正态分布或样本量较小时,传统的参数检验(如t检验)可能不适用。这时,我们需要使用非参数检验方法,如U检验和卡方检验。
检验方法的选择
在选择合适的检验方法时,需要考虑以下因素:
-
下面是一个简单的检验方法选择决策树:
数据类型是什么?
├── 定量数据
│ ├── 正态分布
│ │ ├── 两组:t检验
│ │ └── 多组:方差分析
│ └── 非正态分布
│ ├── 两组:Mann-Whitney U检验
│ └── 多组:Kruskal-Wallis检验
└── 定性数据
├── 期望频数≥5:卡方检验
└── 期望频数<5:Fisher精确检验
Mann-Whitney U检验
理论基础
Mann-Whitney U检验是一种非参数检验方法,用于比较两个独立样本的分布是否有显著差异。它不要求数据呈正态分布,适用于序数数据。
Python实现
import numpy as np
from scipy import stats
import matplotlib.pyplot as plt
# 生成示例数据
np.random.seed(42)
group1 = np.random.normal(loc=5, scale=2, size=30)
group2 = np.random.normal(loc=6, scale=2, size=30)
# 执行U检验
statistic, pvalue = stats.mannwhitneyu(group1, group2, alternative='two-sided')
# 可视化
plt.figure(figsize=(10, 6))
plt.boxplot([group1, group2], labels=['组1', '组2'])
plt.title('两组数据的箱线图比较')
plt.ylabel('值')
plt.show()
print(f'U统计量:{statistic}')
print(f'p值:{pvalue}')
U统计量:293.0
p值:0.020680749139978086
结果解释
-
如果p值 < α(通常为0.05),则拒绝原假设,认为两组数据有显著差异
-
如果p值 ≥ α,则不能拒绝原假设,认为没有足够证据表明两组数据有显著差异
卡方检验
理论基础
卡方检验用于分析分类变量之间是否存在显著关联。它通过比较观察频数与期望频数的差异来判断变量间的独立性。
Python实现
import numpy as np
from scipy.stats import chi2_contingency
import pandas as pd
import seaborn as sns
# 创建示例数据:调查不同年龄段人群的运动习惯
data = np.array([
[30, 20, 10], # 年轻人(经常运动,偶尔运动,很少运动)
[15, 25, 20], # 中年人
[10, 15, 25] # 老年人
])
# 进行卡方检验
chi2, p_value, dof, expected = chi2_contingency(data)
# 创建热力图可视化
plt.figure(figsize=(10, 8))
sns.heatmap(data, annot=True, fmt='d', cmap='YlOrRd',
xticklabels=['经常运动', '偶尔运动', '很少运动'],
yticklabels=['年轻人', '中年人', '老年人'])
plt.title('不同年龄段人群运动习惯分布')
plt.show()
print(f'卡方统计量:{chi2:.2f}')
print(f'p值:{p_value:.4f}')
print(f'自由度:{dof}')
卡方统计量:19.68 p值:0.0006 自由度:4
结果解释
-
-
p值的解释与上述相同,p < 0.05表示变量间存在显著关联
实际应用案例
案例1:医学研究中的U检验
比较两种治疗方法的效果差异:
# 两组患者的恢复时间(天)
treatment_A = [10, 12, 8, 15, 9, 11, 13, 7, 9, 12]
treatment_B = [14, 16, 12, 18, 13, 15, 17, 11, 13, 16]
# 执行U检验
statistic, pvalue = stats.mannwhitneyu(treatment_A, treatment_B)
print(f'p值:{pvalue:.4f}')
if pvalue < 0.05:
print('两种治疗方法的效果有显著差异')
else:
print('没有足够证据表明两种治疗方法的效果有显著差异')
p值:0.0044 两种治疗方法的效果有显著差异