当前位置:   article > 正文

【Python・统计学】(两)多因素方差分析(原理及代码)_python多因素方差分析

python多因素方差分析

前言

自学笔记,分享给对统计学原理不太清楚但需要在论文中用到的小伙伴,欢迎大佬们补充或绕道。ps:本文不涉及公式讲解(文科生小白友好体质)~(部分定义等来源于知乎)

本文重点:多因素方差分析

【1.多因素方差分析简单原理

2.多因素方差分析步骤

3.多因素方差分析代码(配对/独立+事后检验)

1.多因素方差分析简单原理

   多因素方差分析,用于研究一个因变量是否受到多个自变量(也称为因素)的影响,它检验多个因素取值水平的不同组合之间,因变量的均值之间是否存在显著的差异。多因素方差分析既可以分析单个因素的作用(主效应),也可以分析因素之间的交互作用(交互效应),还可以进行协方差分析,以及各个因素变量与协变量的交互作用。

*主效应(Main Effect):
  • 主效应指的是每个因素单独对观测指标(如作物产量)的影响。
  • 在这个例子中,化肥类型的主效应就是不同化肥类型之间作物产量的差异,而土壤类型的主效应就是不同土壤类型之间作物产量的差异。
  • 主效应反映了因素的总体效应,不考虑其他因素的影响。
*交互效应(Interaction Effect):
  • 交互效应指的是两个或多个因素共同作用对观测指标产生的影响,这种影响不能简单地用各因素的主效应相加来解释。
  • 在这个例子中,如果某种化肥在特定的土壤类型上特别有效,而在其他土壤类型上效果一般,这就说明化肥类型和土壤类型存在交互效应。
  • 交互效应反映了因素之间的相互影响和依赖关系。

也就是说,

如果只有主效应显著,说明各因素独立地影响观测指标。

如果交互效应显著,说明因素之间存在相互影响,需要进一步分析交互效应的性质和方向。

2.多因素方差分析步骤

之前学的时候写的笔记(虽然是日语)

  1. ①交互作用の検定
  2. ②交互作用OK: 単純主効果の検定→3水準以上(多重比較)
  3.      交互作用No: 主効果の検定→3水準以上(多重比較)
①首先在做多因素方差分析之前要看数据是否满足前提条件

  检验方差是否满足方差齐性,以及数据的正态性(详情参考之前的t检验单因素方差分析

②检验交互效应(因素之间是否存在显著交互)
  • 如果交互效应显著,说明因素之间存在相互作用,需要进一步分析单纯主效应。
  • 如果交互效应不显著,说明因素之间不存在显著的相互作用,可以直接分析主效应。
③(如果交互效应显著)分析单纯主效应
  • 在每个因素的每个水平下,检验另一个因素的效应是否显著。
  • 如果单纯主效应显著,并且因素有三个或更多水平,进行多重比较以确定哪些水平之间存在显著差异。
④(如果交互效应不显著)分析主效应:
  • 检验每个因素的主效应是否显著。
  • 如果主效应显著,并且因素有三个或更多水平,进行多重比较以确定哪些水平之间存在显著差异。

3.多因素方差分析以及事后比较(独立样本代码)

①读取数据,进行方差齐性检验

使用的是一组教育学数据进行两因素方差分析

有实验组(Group1)和对照组(Group2)进行两种不同的方法教学,其中再把她们分成10人,20人和30人的班(Size),集中教学一段时间后进行测试(成绩为Score)

检验group(教学方法)和班级规模(size)的两因素,是否对最后的学生测试成绩有影响

  1. import pandas as pd
  2. from scipy.stats import levene
  3. from statsmodels.stats.anova import AnovaRM
  4. # 从 CSV 文件读取数据
  5. df = pd.read_csv('/content/taionasi.csv')
  6. balanced_df = pd.DataFrame(columns=df.columns)
  7. # 按照 group 进行抽样,确保每个组的样本大小相同
  8. for group in df['group'].unique():
  9. group_data = df[df['group'] == group]
  10. # 对每个组进行抽样,使得样本大小相同
  11. min_size = min(group_data['size'])
  12. sampled_data = group_data.groupby('size', group_keys=False).apply(lambda x: x.sample(min_size, random_state=42))
  13. # 将抽样后的数据添加到平衡的 DataFrame 中
  14. balanced_df = balanced_df.append(sampled_data, ignore_index=True)
  15. # 检查平衡后的数据结构
  16. print(balanced_df.head())
  17. # 对平衡后的数据进行 Levene's Test
  18. grouped_data_balanced = [balanced_df[balanced_df['group'] == group]['score'].values for group in balanced_df['group'].unique()]
  19. statistic, p_value = levene(*grouped_data_balanced)
  20. # 打印 Levene's Test 的结果
  21. print(f"Levene's Test Statistic: {statistic}")
  22. print(f"P-value: {p_value}")
  23. # 根据 P-value 判断方差齐性
  24. alpha = 0.05 # 有意水準
  25. if p_value < alpha:
  26. print('帰無仮説を棄却:データのグループ間に等分散性がない可能性が高いです。')
  27. else:
  28. print('帰無仮説は棄却されません:データのグループ間に等分散性があると考えられます。')

*注意:检验方差齐性的时候为了确保每组数据的个数一样,进行了数据抽样。如果不进行数据抽样虽然也不会报错但是数据结果截然相反。 

结果:抽样数据显示满足方差齐性,可以进行多因素方差分析 

  1. group size score
  2. 0 1 10 62
  3. 1 1 10 70
  4. 2 1 10 83
  5. 3 1 10 61
  6. 4 1 10 79
  7. Levene's Test Statistic: 1.2774939867588024
  8. P-value: 0.26301796308207803
  9. 帰無仮説は棄却されません:データのグループ間に等分散性があると考えられます。
②用图表检查是因素之间是否存在交互效应 
  1. #交互作用プロット
  2. from statsmodels.graphics.factorplots import interaction_plot
  3. from matplotlib import pyplot as plt # import matplotlib.pyplot as plt グラフを描画するライブラリ
  4. fig = interaction_plot(df['size'], #x軸のデータ
  5. df['group'], #層別するデータ
  6. df['score'], #y軸のデータ
  7. colors=['red', 'blue'], #グラフの色を設定
  8. ms=15) #グラフの点の大きさの設定
  9. plt.show()

 数据存在交点,证明存在交互效应(如果没有交互效应,两条线是平行的)

 ③进行多因素方差分析
  • 导入所需的库:statsmodels
  • 使用ols函数拟合线性模型,模型公式为'score ~ group + size + group:size',表示以score为因变量,group和size为自变量,group:size表示group和size的交互效应
  • 使用anova_lm函数执行方差分析,type=2表示使用II型平方和
  • 将结果表的列名替换为日语
  • 打印方差分析结果表,并注明"交互作用ありの結果"
  1. #二元配置分散分析(交互作用あり)
  2. # 統計モデルを推定するライブラリ
  3. import statsmodels.formula.api as smf
  4. import statsmodels.api as sm
  5. anova_mod = smf.ols('score ~ group + size + group:size', data=df).fit()
  6. taionasi=sm.stats.anova_lm(anova_mod, type=2)
  7. taionasi.columns = ["自由度","平方和","平均平方和","F値","p値"] #列名を日本語に差し替え
  8. print("交互作用ありの結果:"+"\n"+str(taionasi))
  1. 交互作用ありの結果:
  2. 自由度 平方和 平均平方和 F値 p値
  3. group 1.0 26.450000 26.450000 0.261825 6.095178e-01
  4. size 2.0 11238.033333 5619.016667 55.621907 2.108493e-19
  5. group:size 2.0 4057.500000 2028.750000 20.082329 1.421430e-08
  6. Residual 174.0 17577.766667 101.021648 NaN NaN
 ④事后检验
  • 导入所需的库:statsmodels、itertools、pandas
  • 将group和size列的数据类型转换为字符串
  • 初始化一个空的数据框combined_results,用于存储多重比较结果
  • 定义函数run_tukey_comparison,用于执行Tukey's HSD多重比较
    • 对每个group的不同size水平进行两两比较
    • 使用pairwise_tukeyhsd函数进行Tukey's HSD多重比较
    • 提取多重比较结果的重要信息(均值差、置信区间、是否拒绝原假设),并存储到comparison_results数据框中
    • 将comparison_results添加到combined_results数据框中
  • 分别对group1和group2执行run_tukey_comparison函数,进行多重比较
  • 调整combined_results数据框的列顺序
  • 打印合并的多重比较结果
  1. from statsmodels.stats.multicomp import pairwise_tukeyhsd
  2. from itertools import combinations
  3. import pandas as pd
  4. from IPython.display import display, HTML
  5. # df 是你的数据框
  6. # 调整数据类型
  7. df['group'] = df['group'].astype(str)
  8. df['size'] = df['size'].astype(str)
  9. # 初始化一个空的数据框,用于存储多重比较结果
  10. combined_results = pd.DataFrame(columns=['Group', 'Comparison', 'Mean Difference', 'Lower CI', 'Upper CI', 'Reject Null'])
  11. # 定义函数执行多重比较
  12. def run_tukey_comparison(group_label, group_data, size_values):
  13. group_combinations = combinations(group_data, 2)
  14. for size1, size2 in group_combinations:
  15. m_comp = pairwise_tukeyhsd(endog=pd.concat([size1['score'], size2['score']]),
  16. groups=pd.concat([pd.Series([f'{group_label}_size_{size_values[size1.iloc[0]["size"]]}'] * len(size1)),
  17. pd.Series([f'{group_label}_size_{size_values[size2.iloc[0]["size"]]}'] * len(size2))]),
  18. alpha=0.05)
  19. # 提取多重比较结果的重要信息
  20. comparison_results = pd.DataFrame({
  21. 'Group': [f'{group_label}'],
  22. 'Comparison': [f"{size1.iloc[0]['size']} vs {size2.iloc[0]['size']}"],
  23. 'Mean Difference': [m_comp.meandiffs[0]],
  24. 'Lower CI': [m_comp.confint[0, 0]],
  25. 'Upper CI': [m_comp.confint[0, 1]],
  26. 'Reject Null': [m_comp.reject[0]],
  27. })
  28. # 将结果添加到总的数据框中
  29. global combined_results
  30. combined_results = pd.concat([combined_results, comparison_results], ignore_index=True)
  31. # 运行 group1 的多重比较
  32. run_tukey_comparison('group1', group1_sizes, {'10': 10, '20': 20, '30': 30})
  33. # 运行 group2 的多重比较
  34. run_tukey_comparison('group2', group2_sizes, {'10': 10, '20': 20, '30': 30})
  35. # 调整表格显示顺序
  36. combined_results = combined_results[['Group', 'Comparison', 'Mean Difference', 'Lower CI', 'Upper CI', 'Reject Null']]
  37. # 打印合并结果
  38. print("Combined Results:")
  39. display(HTML(combined_results.to_html(index=False)))

事后检验结果:

  1. Group Comparison Mean Difference Lower CI Upper CI Reject Null
  2. group1 10 vs 20 -9.533333 -13.918702 -5.147965 True
  3. group1 10 vs 30 -30.266667 -35.333353 -25.199980 True
  4. group1 20 vs 30 -20.733333 -25.577774 -15.888892 True
  5. group2 10 vs 20 -9.533333 -13.918702 -5.147965 True
  6. group2 10 vs 30 -30.266667 -35.333353 -25.199980 True
  7. group2 20 vs 30 -20.733333 -25.577774 -15.888892 True

总的来说,这些结果表明:

  1. 在 Group1 和 Group2 中,size 水平为 20 的组的平均值显著高于 size 水平为 10 的组。
  2. 在 Group1 和 Group2 中,size 水平为 30 的组的平均值显著高于 size 水平为 10 的组。
  3. 在 Group1 和 Group2 中,size 水平为 30 的组的平均值显著高于 size 水平为 20 的组。

   这些发现表明,不同的 size 水平对因变量有显著影响,并且 size 水平越高,因变量的值越高。此外,Group1 和 Group2 表现出相同的模式,这表明 group 因素可能对 size 水平之间的差异没有显著影响。

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/小桥流水78/article/detail/940793
推荐阅读
相关标签
  

闽ICP备14008679号