Open jmchan88 opened 3 years ago
I'm not going to debug your wall of code. Can you be more specific? "Change the results" how? Maybe you can provide a minimum reproducible example or show the model output and be more specific about what your see vs what you think you should see?
I agree with Greg, a self-contained example would be helpful. How can you reproduce this issue using included data(vbetaFA)
experiment?
But if I had to take a guess based on what wrote, this may relate to how shrinkage is done in the logistic regression (see ?arm::bayesglm and ?MAST::defaultPrior for some details). I expect that setting zlm(, method='glm')
should give invariance to the factor encoding. I also expect that variation in bayesglm due the shrinkage should not be substantial (ie, compared to the standard error of the coefficient).
Yes, factors can be entered into the formula directly, the formula uses model.matrix to generate the design matrix like most of R.
Apologies! I guess my question was more high-level rather than asking to debug. My presupposition is that it should not matter what reference level you choose for a factor to be adjusted. Indeed, that's what seems to be the case if I hard-code the one-hot encodings using model.matrix. On the other hand, if I just use the factor as is in the zlm formula, I get different results depending on what is the reference level.
I'll try to highlight the relevant code below:
In the following, the covariate that I would like to adjust is "tissue" that I feed into the zlm directly as a factor below.
# Prepare for MAST
tissue <- factor(tissue, levels = c('lung','LN','distant')) #Reference level is lung
colData(sca)$treatment = treatment
# Fits
zlmCond <- zlm(~ condition + tissue + cngeneson, sca)
The resulting output changes based on how I set the reference level:
tissue <- factor(tissue, levels = c('lung','LN','distant')) #Reference level is lung
tissue <- factor(tissue, levels = c('LN','lung','distant')) #Reference level is LN
tissue <- factor(tissue, levels = c('distant','LN','lung')) #Reference level is distant
I get the following output:
#Reference level is lung
primerid Pr(>Chisq) coef ci.hi ci.lo fdr
327 FN1 1.27397590106933e-09 0.147043063768172 0.249096390813669 0.0449897367226746 7.51918498184648e-08
#Reference level is LN
primerid Pr(>Chisq) coef ci.hi ci.lo fdr
327 FN1 1.26543559466497e-09 0.154152928165985 0.294230575593857 0.0140752807381125 7.46877889205928e-08
#Reference level is distant
primerid Pr(>Chisq) coef ci.hi ci.lo fdr
327 FN1 1.25377081171509e-09 0.463576811768406 0.675322508262732 0.251831115274079 7.39993170217161e-08
Mainly I see differences in the coef ranging from 0.15 to 0.46. However, if I hard-code the one-hot dummy encoding using model.matrix as follows
tissue <- factor(tissue, levels = c('lung','LN','distant')) #Reference level is lung
tissue_df = data.frame(model.matrix(~tissue))
tissue_df = tissue_df[,2:ncol(tissue_df)]
colnames(tissue_df) = gsub('tissue0','',colnames(tissue_df))
rownames(tissue_df) = names(tissue)
for (i in colnames(tissue_df)) {
colData(sca)[i] <- factor(unlist(as.list(tissue_df[,i])))
}
# Fits
formula = as.formula(paste('~ ', paste(colnames(colData(sca))[2:ncol(colData(sca))], collapse = '+')))
zlmCond <- zlm(formula, sca)
I get the same answer no matter how I choose the reference level.
primerid Pr(>Chisq) coef ci.hi ci.lo fdr
79 FN1 1.1892286821448e-19 0.292507098640155 0.433012762308486 0.152001434971824 2.90533083106261e-17
The idea that variation might occur with bayesglm sounds promising, but I was able to achieve invariance to factor encoding when using model.matrix. I guess my question really is, is that expected? Should I not be feeding factors directly in to the zlm formula for bayesglm, but it should be ok for glm?
Thanks so much!
I can't speculate what the "one hot coding" you implemented actually doing without code that I can run myself, ie,
I have no idea what factor(unlist(as.list(tissue_df[,i]))
does, but it doesn't look idiomatic for a one-hot encoding which I'd expect would use something like model.matrix(~ tissue + 0)
. Nor can I tell what the output you included is supposed to represent, is it a log fold change? Those have their own issues, see ?getLogFC, and you do need to be careful what the reference group is because the contrasts are not a linear function of the coefficients.
Manually generating a design matrix doesn't do anything that you can't do with a factor for glm or bayesglm.
@jmchan88 do you have a reprex
for us to follow up on?
Dear MAST team,
I encountered unexpected behavior when I was including a covariate (tissue) to adjust in my formula.
I noticed that changing the reference level of tissue changes the results!
However, when I instead hard-code the dummy variables for tissue, I not only get different results, but these results don't change based on which reference level is considered. For example:
Does zlm in MAST allow for factors to be entered in the formula directly? My understanding is that when adjusting for a categorical variable, the reference level chosen should not change results, right? Is hard-coding the dummy variables of the factor the right way to do this? Any help/ideas would be greatly appreciated! Thank you!
Joe