#r
#r
Вопрос:
Справочная информация: Я нахожусь в процессе аннотирования SNP из GWAS в организме без особых аннотаций. Я использую объединенную таблицу tBLASTn из UCSC вместе с biomaRt, чтобы сопоставить каждый SNP с вероятным геном (ами).
У меня есть фрейм данных, который выглядит следующим образом:
SNP hu_mRNA gene
chr1.111642529 NM_002107 H3F3A
chr1.111642529 NM_005324 H3F3B
chr1.111801684 BC098118 <NA>
chr1.111925084 NM_020435 GJC2
chr1.11801605 AK027740 <NA>
chr1.11801605 NM_032849 C13orf33
chr1.151220354 NM_018913 PCDHGA10
chr1.151220354 NM_018918 PCDHGA5
В итоге я хотел бы получить одну строку для каждого SNP, а гены и hu_mRNAs разделять запятыми. Вот что мне нужно:
SNP hu_mRNA gene
chr1.111642529 NM_002107,NM_005324 H3F3A
chr1.111801684 BC098118,NM_020435 GJC2
chr1.11801605 AK027740,NM_032849 C13orf33
chr1.151220354 NM_018913,NM_018918 PCDHGA10,PCDHGA5
Теперь я знаю, что могу сделать это одним движением руки в perl, но я действительно хочу сделать все это в R. Есть предложения?
Ответ №1:
Вы могли бы сделать это в одной строке, используя plyr
, поскольку это классическая split-apply-combine
проблема. Вы разбиваете с помощью SNP
, применяете paste
с collapse
помощью и собираете фрагменты обратно во фрейм данных.
plyr::ddply(x, .(SNP), colwise(paste), collapse = ",")
Если вы хотите выполнить data
изменение формы в R в flick of a wrist
, изучите plyr
и reshape2
:). Еще одно простое решение с использованием data.table
, действительно полезное, если вы имеете дело с огромными объемами данных.
data.table::data.table(x)[,lapply(.SD, paste, collapse = ","),'SNP']
Ответ №2:
Вы можете использовать aggregate
with paste
для каждого из них и merge
в конце:
x <- structure(list(SNP = structure(c(1L, 1L, 2L, 3L, 4L, 4L, 5L,
5L), .Label = c("chr1.111642529", "chr1.111801684", "chr1.111925084",
"chr1.11801605", "chr1.151220354"), class = "factor"), hu_mRNA = structure(c(3L,
4L, 2L, 7L, 1L, 8L, 5L, 6L), .Label = c("AK027740", "BC098118",
"NM_002107", "NM_005324", "NM_018913", "NM_018918", "NM_020435",
"NM_032849"), class = "factor"), gene = structure(c(4L, 5L, 1L,
3L, 1L, 2L, 6L, 7L), .Label = c("<NA>", "C13orf33", "GJC2", "H3F3A",
"H3F3B", "PCDHGA10", "PCDHGA5"), class = "factor")), .Names = c("SNP",
"hu_mRNA", "gene"), class = "data.frame", row.names = c(NA, -8L
))
a1 <- aggregate(hu_mRNA~SNP,data=x,paste,sep=",")
a2 <- aggregate(gene~SNP,data=x,paste,sep=",")
merge(a1,a2)
SNP hu_mRNA gene
1 chr1.111642529 NM_002107, NM_005324 H3F3A, H3F3B
2 chr1.111801684 BC098118 <NA>
3 chr1.111925084 NM_020435 GJC2
4 chr1.11801605 AK027740, NM_032849 <NA>, C13orf33
5 chr1.151220354 NM_018913, NM_018918 PCDHGA10, PCDHGA5
Комментарии:
1. Блестяще!! Спасибо! Я не знал
aggregate
функции. Я немного изменил, чтобы убрать пробелы после запятых, например:a1 <- aggregate(hu_mRNA~SNP,data=x,paste,collapse=",") a2 <- aggregate(gene~SNP,data=x,paste,collapse=",")
2. @caddymob Хороший вызов, кажется, что
sep
на самом деле это не имеет никакого эффекта в этом случае, толькоcollapse
действует.3. @Джеймс. Решение Габора предполагало, что будет работать однострочный вариант с
collapse=","
.
Ответ №3:
Сначала настройте тестовые данные. Обратите внимание, что мы сделали столбцы "character"
классовыми, а не "factor"
с помощью as.is=TRUE
:
Lines <- "SNP hu_mRNA gene
chr1.111642529 NM_002107 H3F3A
chr1.111642529 NM_005324 H3F3B
chr1.111801684 BC098118 <NA>
chr1.111925084 NM_020435 GJC2
chr1.11801605 AK027740 <NA>
chr1.11801605 NM_032849 C13orf33
chr1.151220354 NM_018913 PCDHGA10
chr1.151220354 NM_018918 PCDHGA5"
cat(Lines, "n", file = "data.txt")
DF <- read.table("data.txt", header = TRUE, na.strings = "<NA>", as.is = TRUE)
Теперь попробуйте этот aggregate
оператор:
> aggregate(. ~ SNP, DF, toString)
SNP hu_mRNA gene
1 chr1.111642529 NM_002107, NM_005324 H3F3A, H3F3B
2 chr1.111925084 NM_020435 GJC2
3 chr1.11801605 NM_032849 C13orf33
4 chr1.151220354 NM_018913, NM_018918 PCDHGA10, PCDHGA5
Комментарии:
1. И по тому же принципу это должно увенчаться успехом:
aggregate(. ~ SNP, DF, paste, collapse=",")
Ответ №4:
Это также можно решить с помощью операций reshape2
‘s melt
и dcast
. При таком подходе melt
сначала преобразуются данные в «длинный» формат, а затем значения dcast
редактируются с помощью той же операции, paste(..., collapse = ",")
:
library(reshape2)
x <- read.table(
stringsAsFactors = FALSE,
header = TRUE,
na.strings = "<NA>",
text = " SNP hu_mRNA gene
chr1.111642529 NM_002107 H3F3A
chr1.111642529 NM_005324 H3F3B
chr1.111801684 BC098118 <NA>
chr1.111925084 NM_020435 GJC2
chr1.11801605 AK027740 <NA>
chr1.11801605 NM_032849 C13orf33
chr1.151220354 NM_018913 PCDHGA10
chr1.151220354 NM_018918 PCDHGA5")
(xm <-melt(x, id.vars = "SNP", na.rm = TRUE))
## SNP variable value
## 1 chr1.111642529 hu_mRNA NM_002107
## 2 chr1.111642529 hu_mRNA NM_005324
## 3 chr1.111801684 hu_mRNA BC098118
## 4 chr1.111925084 hu_mRNA NM_020435
## 5 chr1.11801605 hu_mRNA AK027740
## 6 chr1.11801605 hu_mRNA NM_032849
## 7 chr1.151220354 hu_mRNA NM_018913
## 8 chr1.151220354 hu_mRNA NM_018918
## 9 chr1.111642529 gene H3F3A
## 10 chr1.111642529 gene H3F3B
## 12 chr1.111925084 gene GJC2
## 14 chr1.11801605 gene C13orf33
## 15 chr1.151220354 gene PCDHGA10
## 16 chr1.151220354 gene PCDHGA5
(xc <- dcast(xm, SNP~variable, fun.aggregate = paste, collapse = ","))
## SNP hu_mRNA gene
## 1 chr1.111642529 NM_002107,NM_005324 H3F3A,H3F3B
## 2 chr1.111801684 BC098118
## 3 chr1.111925084 NM_020435 GJC2
## 4 chr1.11801605 AK027740,NM_032849 C13orf33
## 5 chr1.151220354 NM_018913,NM_018918 PCDHGA10,PCDHGA5
Ответ №5:
Вот dplyr
решение, какой IHMO является наиболее читаемым:
library(dplyr)
x %>%
group_by(SNP) %>%
summarize(
genes = paste(gene, collapse = ','),
hu_mRNA = paste(hu_mRNA, collapse = ',')
)
Результат:
Source: local data frame [5 x 3]
SNP genes hu_mRNA
(fctr) (chr) (chr)
1 chr1.111642529 H3F3A,H3F3B NM_002107,NM_005324
2 chr1.111801684 <NA> BC098118
3 chr1.111925084 GJC2 NM_020435
4 chr1.11801605 <NA>,C13orf33 AK027740,NM_032849
5 chr1.151220354 PCDHGA10,PCDHGA5 NM_018913,NM_018918