2015-03-30 2 views
0

StackOverflow вопросПересечение кадров несколько данных в R

Привет ребята,

Я пытаюсь «крест» несколько dataframes с R.

Мои кадры данных, поступающих из экспериментов секвенирования с высокой пропускной способностью и выглядят как следующие:

df1:

  chr pos orient weight in_nucleosome in_subtelo 
1 NC_001133 999  +  1   TRUE  TRUE 
2 NC_001133 1505  -  14   FALSE  TRUE 
3 NC_001133 1525  -  2   TRUE  TRUE 
4 NC_001134 480  +  1   TRUE  TRUE 
5 NC_001134 509  +  2   FALSE  TRUE 
6 NC_001134 539  +  3   FALSE  TRUE 
7 NC_001135 1218  +  1   TRUE  TRUE 
8 NC_001135 1228  +  2   TRUE  TRUE 
9 NC_001135 1273  +  1   TRUE  TRUE 
10 NC_001136 362  +  1   TRUE  TRUE 

и

df2:

  chr    feature start end orient 
1 NC_001133     ARS 707 776  . 
2 NC_001133     ARS 7997 8547  . 
3 NC_001133     ARS 30946 31183  . 
4 NC_001133 ARS_consensus_sequence 31002 31018  + 
5 NC_001133 ARS_consensus_sequence 70418 70434  - 
6 NC_001133 ARS_consensus_sequence 124463 124479  - 
7 NC_001136 blocked_reading_frame 721071 721481  - 
8 NC_001137 blocked_reading_frame 375215 377614  - 
9 NC_001141 blocked_reading_frame 29032 30048  + 
10 NC_001133     CDS 335 649  + 

То, что я хочу сделать, это знать, для данной хромосоме ("Chr" здесь) и для каждого df2 $ функции или нет (df2 $ начать < df1 $ поз < df2 $ end). Затем я хотел бы добавить столбец в df1, имя которого было бы одним из рассмотренных df2feature и заполнено TRUE или FALSE в отношении условия, указанного ранее.

Я уверен, что семейство функций apply должно использоваться, возможно, вложенное в один antoher, но после нескольких часов попыток я не могу этого сделать.

Я сделал это в очень неэлегантном, длинном и подверженном ошибкам способе с вложенными циклами, но я убежден, что есть более простое и, возможно, более быстрое решение.

Спасибо за чтение этого,

Antoine.

+2

Вы можете попробовать '' foverlaps' из data.table' или '' findOverlaps' из библиотеки (GenomicRanges) ' – akrun

+0

Можете ли вы предоставить данные, которые обеспечили бы * некоторые * Матчи? Я не вижу ничего, что бы соответствовало вашим ограничениям. – r2evans

+0

Благодаря вам я реализую свой пример, где не так хорошо выбрали, и в моем вопросе были опечатки. Я сразу же обновлю его. –

ответ

0

Хотя это может быть возможным с dplyr (я пробовал, но я не то, что опытный), я получил его на работу (я думаю) с foreach и iterators:

Ваши данные:

df1 <- structure(list(chr = c("NC_001133", "NC_001133", "NC_001133", "NC_001134", "NC_001134", "NC_001134", "NC_001135", "NC_001135", "NC_001135", "NC_001136"), 
         pos = c(999L, 1505L, 1525L, 480L, 509L, 539L, 1218L, 1228L, 1273L, 362L), 
         orient = c("+", "-", "-", "+", "+", "+", "+", "+", "+", "+"), 
         weight = c(1L, 14L, 2L, 1L, 2L, 3L, 1L, 2L, 1L, 1L), 
         in_nucleosome = c(TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE), 
         in_subtelo = c(TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE)), 
       .Names = c("chr", "pos", "orient", "weight", "in_nucleosome", "in_subtelo"), 
       class = "data.frame", 
       row.names = c("1", "2", "3", "4", "5", "6", "7", "8", "9", "10")) 

df2 <- structure(list(chr = c("NC_001133", "NC_001133", "NC_001133", "NC_001133", "NC_001133", "NC_001133", "NC_001136", "NC_001137", "NC_001141", "NC_001133"), 
         feature = c("ARS", "ARS", "ARS", "ARS_consensus_sequence", "ARS_consensus_sequence", "ARS_consensus_sequence", "blocked_reading_frame", "blocked_reading_frame", "blocked_reading_frame", "CDS"), 
         start = c(707L, 7997L, 30946L, 31002L, 70418L, 124463L, 721071L, 375215L, 29032L, 335L), 
         end = c(776L, 8547L, 31183L, 31018L, 70434L, 124479L, 721481L, 377614L, 30048L, 649L), 
         orient = c(".", ".", ".", "+", "-", "-", "-", "-", "+", "+")), 
       .Names = c("chr", "feature", "start", "end", "orient"), 
       class = "data.frame", 
       row.names = c("1", "2", "3", "4", "5", "6", "7", "8", "9", "10")) 

С Я думаю, что ваши данные не имеют никаких совпадений, я впрыснуть некоторые из них:

## to be able to find *something* 
df1$pos <- c(999, 1505, 8000, 480, 509, 539, 1218, 1228, 1272, 721072) 

код:

library(foreach) 
library(iterators) 

## pre-populate df1 with necessary columns 
for (col in unique(df2$feature)) df1[,col] <- FALSE 

df1a <- foreach (subdf1 = iter(df1, by='row'), .combine=rbind) %do% { 
    features <- unique(df2$feature[df2$chr== subdf1$chr]) 
    for (feature in features) { 
     idx <- (df2$chr == subdf1$chr) & (feature == df2$feature) 
     if (length(idx)) { 
      subdf1[feature] <- any((df2$start[idx] < subdf1$pos) & (subdf1$pos < df2$end[idx])) 
     } 
    } 
    subdf1 
} 

df1a 
##   chr pos orient weight in_nucleosome in_subtelo ARS 
## 1 NC_001133 999  +  1   TRUE  TRUE FALSE 
## 2 NC_001133 1505  -  14   FALSE  TRUE FALSE 
## 3 NC_001133 8000  -  2   TRUE  TRUE TRUE 
## 4 NC_001134 480  +  1   TRUE  TRUE FALSE 
## 5 NC_001134 509  +  2   FALSE  TRUE FALSE 
## 6 NC_001134 539  +  3   FALSE  TRUE FALSE 
## 7 NC_001135 1218  +  1   TRUE  TRUE FALSE 
## 8 NC_001135 1228  +  2   TRUE  TRUE FALSE 
## 9 NC_001135 1272  +  1   TRUE  TRUE FALSE 
## 10 NC_001136 721072  +  1   TRUE  TRUE FALSE 
## ARS_consensus_sequence blocked_reading_frame CDS 
## 1     FALSE     FALSE FALSE 
## 2     FALSE     FALSE FALSE 
## 3     FALSE     FALSE FALSE 
## 4     FALSE     FALSE FALSE 
## 5     FALSE     FALSE FALSE 
## 6     FALSE     FALSE FALSE 
## 7     FALSE     FALSE FALSE 
## 8     FALSE     FALSE FALSE 
## 9     FALSE     FALSE FALSE 
## 10     FALSE     TRUE FALSE 

простой побочный эффект использования foreach и iterators является то, что, если данные велико, и вы используете doParallel, просто замените %do% с %dopar% и вещи идут как параллельно, как вы определили. Вы могли бы предварить все вышеперечисленное что-то вроде:

library(doParallel) 
cl <- makeCluster(detectCores() - 1) # leaving one available is "A Good Thing (tm)" 
registerDoParallel(cl) 

## replace %do% with %dopar%, do all of the above code 

## clean up 
stopCluster(cl) 
+0

Я постараюсь понять и освоить ваш код, тогда я попробую его на реальных фреймах данных и обновить этот пост. –

+0

Ваш код отлично работает на приведенном здесь примере, но не работает с моими реальными данными без каких-либо ошибок, он просто запускается и никогда не заменяет FALSE по TRUE, когда это необходимо.Это похоже на то, что условие никогда не выполнялось, я попробовал 'for (col in unique (функция df2 $)) df1 [, col] <-" XXX "' и он никогда не заменяет «XXX». Я не уверен, что мне удастся отладить это. Я постараюсь работать над запутанным решением с петлями и надеюсь, что кто-то может объяснить, как получить тот же результат с помощью какого-то четырехстрочного с dplyer или ddply! Спасибо за ваше время. –

+0

Являются ли 'df1' и' df2' просто подмножествами истинных данных, или вы произвольно и отдельно их создавали? Возможно, что-то есть в данных, которые я не вижу здесь. – r2evans

Смежные вопросы