How to specify lm model matrix

和自甴很熟 提交于 2019-12-12 03:22:44

问题


I have measurements obtained from 2 groups where each group has the same 3 levels. Here's my example data.frame:

df <- data.frame(measurement = c(rnorm(10,1,1),rnorm(10,0.75,1),rnorm(10,1.25,1),
                rnorm(10,0.5,1),rnorm(10,1.75,1),rnorm(10,0.25,1)),
                group = as.factor(c(rep("a",30),rep("b",30))),
                level = as.factor(rep(c(rep("x",10),rep("y",10),rep("z",10)),2)))

I'm interested in quantifying how measurement in each level is affected by group.

I guess a linear model (lm) is the appropriate approach for this, where the group:level interaction terms capture the effects I'm interested in.

Is there a way to specify an lm that will only compute these interaction terms: groupb:levelx, groupb:levely, and groupb:levelz? I believe this tells me how each level is affected by group "b" (relative to group "a"), which I think is what I'm interested in.

The closest I got is:

lm(measurement ~ 0 + group * level - group, data = df)

But that still computes the effects of levelx, levely, and levelz, which I'm not interested in.


回答1:


As @Lyzander mentioned above you should clarify a bit more what you want. Based on what you said "how measurement is affected by group "b" (relative to group "a") for each level", I guess there are 3 simple ways to do that.

df <- data.frame(measurement = c(rnorm(10,1,1),rnorm(10,0.75,1),rnorm(10,1.25,1),
                                 rnorm(10,0.5,1),rnorm(10,1.75,1),rnorm(10,0.25,1)),
                 group = as.factor(c(rep("a",30),rep("b",30))),
                 level = as.factor(rep(c(rep("x",10),rep("y",10),rep("z",10)),2)))


library(dplyr)

#### calculate stats (mean values) ---------------------------------------------
df %>% group_by(level, group) %>% summarise(MeanMeasurement = mean(measurement))

#     level  group MeanMeasurement
#    (fctr) (fctr)           (dbl)
# 1      x      a       1.6708659
# 2      x      b       0.8487751
# 3      y      a       0.7977769
# 4      y      b       1.4209206
# 5      z      a       1.5484668
# 6      z      b      -0.3244225

#### build a model for each level ---------------------------------------------
summary(lm(measurement ~ group  , data = df[df$level=="x",]))

# Coefficients:
#   Estimate Std. Error t value Pr(>|t|)    
# (Intercept)   1.6709     0.3174   5.264 5.27e-05 ***
#   groupb       -0.8221     0.4489  -1.831   0.0837 .


summary(lm(measurement ~ group  , data = df[df$level=="y",]))

# Coefficients:
#   Estimate Std. Error t value Pr(>|t|)   
# (Intercept)   0.7978     0.2565   3.111  0.00604 **
#   groupb        0.6231     0.3627   1.718  0.10295


summary(lm(measurement ~ group  , data = df[df$level=="z",]))

# Coefficients:
#   Estimate Std. Error t value Pr(>|t|)    
# (Intercept)   1.5485     0.3549   4.363 0.000375 ***
#   groupb       -1.8729     0.5019  -3.731 0.001528 **



## build a model only with interactions ------------------------------------------
summary(lm(measurement ~ group : level , data = df))

# Coefficients: (1 not defined because of singularities)
# Estimate Std. Error t value Pr(>|t|)    
# (Intercept)    -0.3244     0.3123  -1.039 0.303452    
# groupa:levelx   1.9953     0.4416   4.518 3.43e-05 ***
#   groupb:levelx   1.1732     0.4416   2.657 0.010354 *  
#   groupa:levely   1.1222     0.4416   2.541 0.013951 *  
#   groupb:levely   1.7453     0.4416   3.952 0.000227 ***
#   groupa:levelz   1.8729     0.4416   4.241 8.76e-05 ***
#   groupb:levelz       NA         NA      NA       NA 

If you check the stats (1st approach) and the models' coefficients you'll see that all those 3 approaches agree with each other.

I'd go with the 2nd approach as it is the only one that gives you info about whether a difference of group (a vs b) within a level is statistically significant or not. 1st approach just reports means. 3rd approach includes p values but they correspond to comparisons with a baseline interaction value and not to comparisons between groups a and b.

You mentioned "ONLY compute these interaction terms: groupb:levelx, groupb:levely, and groupb:levelz" which means that you won't get the other 3 interactions of a and x,y,z. In other words you force your model to include those 3 interactions.

You can do that manually like this

df <- data.frame(measurement = c(rnorm(10,1,1),rnorm(10,0.75,1),rnorm(10,1.25,1),
                                 rnorm(10,0.5,1),rnorm(10,1.75,1),rnorm(10,0.25,1)),
                 group = as.factor(c(rep("a",30),rep("b",30))),
                 level = as.factor(rep(c(rep("x",10),rep("y",10),rep("z",10)),2)))

library(dplyr)

df %>%
  mutate(interactions = paste0(group,":",level),
         interactions = ifelse(group=="a","a",interactions)) -> df2

summary(lm(measurement ~ interactions, data = df2))

# Coefficients:
#   Estimate Std. Error t value Pr(>|t|)    
# (Intercept)       0.9318     0.1831   5.089 4.36e-06 ***
#   interactionsb:x  -0.7803     0.3662  -2.131  0.03752 *  
#   interactionsb:y   0.2747     0.3662   0.750  0.45638    
# interactionsb:z  -1.1367     0.3662  -3.104  0.00299 ** 

but now the other 3 interactions are combined and every time you compare each one of your 3 interactions (b:x, b:y, b:z) with the general group a. You don't compare a vs. b within x,y and z but you compare x vs. y vs. z within group b.




回答2:


Based on this sentence: "Is there a way to specify an lm that will only compute these interaction terms: groupb:levelx, groupb:levely, and groupb:levelz?", I think you just want:

lm( measurement ~ level +0, subset = group=="b", data = df)


来源:https://stackoverflow.com/questions/33527089/how-to-specify-lm-model-matrix

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!