如何从statsmodels的MNLogit中获取Rao得分及相关问题咨询
计数表多分类分析解决方案
一、MNLogit场景下的Rao得分检验实现
如果一定要用statsmodels的MNLogit做Rao得分检验,score_test函数核心是传入约束条件对应的参数或约束矩阵,具体操作如下:
- 先拟合无约束模型:
import statsmodels.api as sm model = sm.MNLogit(y, X) unconstrained_result = model.fit()
- 两种常见约束的调用方式:
检验单个自变量系数全为0:
假设要约束第2个自变量(索引1)的所有类别系数为0,构造约束矩阵和约束值:import numpy as np K_minus_1 = unconstrained_result.params.shape[0] // X.shape[1] p = X.shape[1] # 构造约束矩阵:定位目标自变量的系数行 R = np.zeros((K_minus_1, K_minus_1*p)) for i in range(K_minus_1): R[i, i*p + 1] = 1 q = np.zeros(K_minus_1) # 约束值设为0 # 执行得分检验 score_stat, score_pval, _ = unconstrained_result.score_test(R, q) print(f"Rao得分统计量: {score_stat}, p值: {score_pval}")检验全局模型显著性(所有自变量系数为0):
直接传入零模型的参数即可:null_model = sm.MNLogit(y, sm.add_constant(np.zeros_like(y))) null_result = null_model.fit() score_stat, score_pval, _ = unconstrained_result.score_test(null_result.params)
二、更适配计数数据的替代方案
MNLogit是针对离散因变量的回归,你的数据本质是列联表/计数表,以下方法更合适:
1. 对数线性模型(列联表标准分析方法)
直接建模计数的对数与类别变量的关系,支持小样本场景,还能处理过度离散:
import statsmodels.api as sm from statsmodels.formula.api import glm # 假设数据已转长格式:count ~ category + other_features # 泊松族(适合无过度离散) model = glm("count ~ category", data=long_data, family=sm.families.Poisson()) result = model.fit() # 似然比检验p值 print(result.llr_pvalue) # Rao得分检验(对比零模型) null_model = glm("count ~ 1", data=long_data, family=sm.families.Poisson()) null_result = null_model.fit() score_stat, score_pval = result.score_test(null_result.params) print(f"Rao得分p值: {score_pval}") # 存在过度离散时改用负二项族 # model = glm("count ~ category", data=long_data, family=sm.families.NegativeBinomial())
2. 卡方类检验(针对列联表独立性)
- 皮尔逊卡方/ Fisher精确检验(小样本首选):
from scipy.stats import chi2_contingency, fisher_exact # count_matrix是你的原始计数表矩阵 chi2, p_chi, dof, expected = chi2_contingency(count_matrix) # 单元格期望计数<5时用Fisher精确检验 if (expected < 5).any(): odds_ratio, p_fisher = fisher_exact(count_matrix) print(f"Fisher精确检验p值: {p_fisher}") - 似然比卡方检验:
import numpy as np from scipy.stats import chi2 observed = count_matrix expected = chi2_contingency(observed)[3] lr_stat = 2 * np.sum(observed * np.log(observed/expected)) lr_pval = chi2.sf(lr_stat, dof) print(f"似然比卡方p值: {lr_pval}")
三、GPU加速拟合方案
1. RAPIDS cuML库(GPU原生统计模型)
适合大规模计数数据,支持多分类回归和对数线性模型:
import cudf from cuml import LogisticRegression from cuml.glm import GLM # 转成cuDF格式(GPU兼容数据结构) gdf = cudf.DataFrame(long_data) # GPU版多分类逻辑回归(适配MNLogIT格式数据) model = LogisticRegression(multi_class="multinomial", solver="qn") model.fit(gdf[X_cols], gdf['y']) # GPU版对数线性模型(泊松/负二项) glm_model = GLM(family='poisson', penalty='none') glm_model.fit(gdf[feature_cols], gdf['count'])
2. TensorFlow/PyTorch自定义实现
如果需要灵活定制模型,用深度学习框架做GPU加速的计数模型:
import tensorflow as tf # 泊松回归示例 model = tf.keras.Sequential([ tf.keras.layers.Dense(units=1, activation='exponential', input_shape=(feature_num,)) ]) model.compile(optimizer='adam', loss='poisson') # GPU训练 model.fit(X_tensor, count_tensor, epochs=50, batch_size=32)
补充:计数表转MNLogIT格式方法
如果坚持用MNLogit,需要把计数表展开为个体级长格式数据:
import pandas as pd # count_df是宽格式计数表:行=特征,列=类别,值=计数 long_df = count_df.stack().reset_index(name='count') # 按计数重复行,生成个体样本 expanded_df = long_df.loc[long_df.index.repeat(long_df['count'])] y = expanded_df['category'] X = pd.get_dummies(expanded_df['feature'], drop_first=True)
内容的提问来源于stack exchange,提问作者donkey
相关产品推荐
相关产品推荐

