I have a dataframe of expression data where gene are rows and columns are samples. I also have a dataframe containing metadata for each sample in the expression dataframe. In reality my expr dataframe has 30,000+ rows and 100+ columns. However, below is an example with smaller data.
expr <- data.frame(sample1 = c(1,2,2,0,0),
sample2 = c(5,2,4,4,0),
sample3 = c(1,2,1,0,1),
sample4 = c(6,5,6,6,7),
sample5 = c(0,0,0,1,1))
rownames(expr) <- paste0("gene",1:5)
meta <- data.frame(sample = paste0("sample",1:5),
treatment = c("control","control",
"treatment1",
"treatment2", "treatment2"))
I want to find the mean for each gene per treatment. From the examples I've seen with split() or group_by() people group based on a column already present in the data.frame. However, I have a separate dataframe (meta) that classifies the grouping for the columns in another dataframe (expr).
I would like my output to be a dataframe with genes as rows, treatment as columns, and values as the mean.
# control treatment1 treatment2
# gene1 mean mean mean
# gene2 mean mean mean
An approach in base R which works for the particular toy data example given:
colnames(expr) = paste0(colnames(expr), "_",
meta$treatment[match(colnames(expr), meta$sample)])
vapply(unique(meta$treatment),
\(i) rowMeans(expr[grepl(i, colnames(expr))]), numeric(nrow(expr)))
#> control treatment1 treatment2
#> gene1 3 1 3.0
#> gene2 2 2 2.5
#> gene3 3 1 3.0
#> gene4 2 0 3.5
#> gene5 0 1 4.0
Data
expr <- data.frame(sample1 = c(1,2,2,0,0),
sample2 = c(5,2,4,4,0),
sample3 = c(1,2,1,0,1),
sample4 = c(6,5,6,6,7),
sample5 = c(0,0,0,1,1))
rownames(expr) <- paste0("gene",1:5)
meta <- data.frame(sample = paste0("sample",1:5),
treatment = c("control","control",
"treatment1",
"treatment2", "treatment2"))
A base R approach:
expr|>
split.default(with(meta, treatment[match(names(expr), sample)]))|>
lapply(rowMeans)|>
structure(dim=3)|>
array2DF()
Var1 gene1 gene2 gene3 gene4 gene5
1 control 3 2.0 3 2.0 0
2 treatment1 1 2.0 1 0.0 1
3 treatment2 3 2.5 3 3.5 4
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With