为什么 emtrends() 设置 type="response" 后结果不变?
结论
对于给出的模型,两段代码得到相同的趋势估计和两两比较结果,这与 emtrends() 的处理方式一致。
type = "response" 不会自动将已计算的斜率转换为原始 y 尺度上的斜率。如果要计算反变换后的预测曲线关于 x 的变化率,应在调用 emtrends() 时使用 regrid = "response",并指定计算所用的 x 值。
为什么 type = “response” 没有改变结果?
原始模型为:
model <- data %>% lm(log(y) ~ log(x) * w, data = .)
对于 w 的某个水平,模型的条件期望可以写成:
[ \eta_w(x)=E[\log(y)\mid x,w]=a_w+b_w\log(x). ]
交互项允许不同的 w 水平有不同的斜率 (b_w)。原代码指定了 var = "x",因此计算得到的趋势近似为:
[ \frac{d\eta_w(x)}{dx}=\frac{b_w}{x}. ]
它表示 x 变化时拟合的 log(y) 的变化率,既不是 (b_w) 本身,也不是原始 y 尺度上的变化率。emtrends() 用预测值的有限差分估计这些局部趋势,数值结果因此可能与解析导数有小的近似误差。emtrends() 官方文档
type = "response" 通常在汇总时用于反变换,不会改变此前求差分所用的预测尺度。当前实现会在计算趋势后清除原响应的变换信息,因此也不会按 log 响应对这些趋势进行指数反变换。这解释了为什么 $emtrends 和 $contrasts 都没有变化。变换处理说明、emtrends() 源码
从数学上看,也不能直接对斜率取指数:
[ \exp\left(\frac{d\eta_w(x)}{dx}\right) \ne \frac{d\exp(\eta_w(x))}{dx}. ]
根据需要选择趋势尺度
比较 log(y) 关于 log(x) 的斜率
如果要比较模型中各组的 (b_w),可将 var 设置为 "log(x)":
library(emmeans)
tr_logx <- emtrends(
model,
specs = revpairwise ~ w,
var = "log(x)",
adjust = "bonferroni",
level = 0.9
)
summary(tr_logx, infer = TRUE)
对应的量为:
[ \frac{d\eta_w(x)}{d\log(x)}=b_w. ]
在这个模型中,该斜率不随 x 改变。它也可以解释为反变换拟合曲线的弹性:x 增加约 1% 时,曲线的预测值约改变 (b_w)%。这是小幅变化下的近似解释。
比较 log(y) 关于原始 x 的局部斜率
保留 var = "x",并指定一个有实际意义的正数 x0:
# 示例取数据中 x 的中位数;使用前确认它是有效的正数
x0 <- median(data$x, na.rm = TRUE)
tr_x <- emtrends(
model,
specs = revpairwise ~ w | x,
var = "x",
at = list(x = x0),
adjust = "bonferroni",
level = 0.9
)
summary(tr_x, infer = TRUE)
这里比较的是各组在同一个 x0 处的 (b_w/x_0)。显式指定 at 可以避免将参考网格中的默认取值误当成对所有观测位置的平均斜率。
比较原始 y 尺度上的局部斜率
如果要先将预测值反变换到 y 尺度,再计算其关于 x 的变化率,可以使用:
tr_response <- emtrends(
model,
specs = revpairwise ~ w | x,
var = "x",
at = list(x = x0),
regrid = "response",
adjust = "bonferroni",
level = 0.9
)
summary(tr_response, infer = TRUE)
这里,regrid = "response" 在计算差分前转换预测值,从而改变所估计的趋势。项目维护者对处理顺序的说明
默认不进行偏差校正时,反变换后的拟合曲线为:
[ \widetilde y_w(x)=\exp(\eta_w(x)) =\exp(a_w)x^{b_w}. ]
根据链式法则,这条曲线关于 x 的导数为:
[ \frac{d\widetilde y_w(x)}{dx} =\widetilde y_w(x)\frac{b_w}{x}. ]
因此,原始响应尺度上的斜率取决于组别、x 的位置以及该位置的预测值;组间比较的结果也可能与 log 尺度上的比较不同。
解释结果时需要注意什么?
- 模型使用
log(x)和log(y),参与拟合的数据必须满足相应的定义域要求;计算趋势的参考点及差分点也必须有效。 exp(E[log(y) | x, w])通常不等于E[y | x, w]。如果目标是原始 y 的条件算术均值及其导数,还需要根据残差分布考虑反变换偏差。adjust = "bonferroni"和level = 0.9控制推断设置,不决定趋势在哪个尺度上计算。- 原始材料没有提供数据、数值输出或安装的 emmeans 版本,因此无法复核具体估计值。上述结论说明的是代码所定义的估计目标和尺度处理方式。
备注:内容仅供参考。
