Фон: Я собираюсь предоставить фон для применения этого кода и программный фон.Надеюсь, оба помогут.Я занимаюсь вычислительной работой в области геномики.Да, просто еще один биолог, выдававший себя за компьютерщика.Я работаю над сценарием, который позволит мне интегрировать наборы данных по каждой позиции в геноме человека.Это переводит в фрейм данных, который составляет более 3 миллиардов строк на 12 столбцов.В качестве тестового набора данных я строю свой конвейер анализа с использованием дрожжевого генома, который сгенерирует кадр данных с примерно 25 миллионами строк и 12 столбцами.
Проблема: Мой текущий код работаетхорошо, но жестоко медленно.Например, я запустил свой трубопровод 45 минут назад, и он составляет около 1/3 пути через дрожжевой геном.Это означает, что, вероятно, потребуется 135 минут, чтобы закончить один образец дрожжей, или 270 часов для 1 образца человека ... теперь умножьте это на 90 образцов человека, которые я готовлю к анализу, и вы можете надеяться увидеть мою проблему.Мне нужно ускорить это.Я буду распараллеливать это, но даже тогда я думаю, что сам код слишком неуклюжий.Я хочу помочь моей существующей функции намного, намного быстрее.Пожалуйста, не говорите мне, что мне нужно распараллелить это (это получит отрицательный голос).
Пример данных:
chrom <- c("chr1", "chr1", "chr1", "chr1")
start <- c("0","1","2","6")
stop <- c("1","2","6","7")
sequence <- c("a", "t", "tcag", "a")
seqData <- data.frame(chrom, start, stop, sequence)
Пример вывода:
chrom_out <- c("chr1", "chr1", "chr1", "chr1", "chr1", "chr1", "chr1")
start_out <- c("0", "1", "2", "3", "4", "5", "6")
stop_out <- c("1", "2", "3", "4", "5", "6", "7")
sequence_out <- c("a", "t", "t", "c", "a", "g", "a")
out_seqdata <- data.frame(chrom_out, start_out, stop_out, sequence_out)
Текущий код:
library(dplyr)
library(stringi)
library(stringr)
wl = function(x){
length<- stri_length(x["sequence"])
if(length ==1){
tmpseq<- x["sequence"]
tmpstart <- as.numeric(x["start"])
tmpstop <- as.numeric(x["stop"])
tmpchrom <- x["chrom"]
tmpdf <- data.frame(tmpseq, tmpstart, tmpstop, tmpchrom)
colnames(tmpdf)<- c("tmpseq", "tmpstart", "tmpstop", "tmpchrom")
print(tmpdf)
}else{
tmpseq<- strsplit(x["sequence"], "(?<=.{1})", perl = TRUE)
tmpstart <- as.numeric(x["start"])+(1:length-1)
tmpstop<- as.numeric(x["start"])+(1:length)
tmpdf <- data.frame(tmpseq, tmpstart, tmpstop)
tmpdf$tmpchrom <- x["chrom"]
colnames(tmpdf)<- c("tmpseq", "tmpstart", "tmpstop", "tmpchrom")
print(tmpdf)
}
}
Объяснение кода: Я использую apply для итерации по каждой строке кадра данных.Фрейм данных представляет собой список координат и геномную последовательность для этих координат.Chrom = хромосома, start = начальная позиция в хромосоме, stop = позиция остановки, а последовательность - это фактическая последовательность.Данные в настоящее время представлены в сжатом формате, примером которого является третий ряд данных.Я хочу расширить эти данные таким образом, чтобы каждая геномная буква стала отдельной строкой, а затем соответствующим образом скорректировать диапазон координат.Функция wl (от широкого до длинного) выполняет это.Сначала он определяет длину строки последовательности.Если длина равна 1, она возвращает эту строку в качестве кадра данных без дальнейших манипуляций;иначе он разбивает строку на отдельные символы, определяет координаты для каждого символа и возвращает этот фрейм данных.В результате получается список фреймов данных, которые затем объединяются, производя выходные данные примера.
Что мне нужно: Я собираюсь разбить геном на части, создав список, что позволит мнераспараллелить этот список.Чанки приведут к серии кадров длиной около 25 миллионов строк.Я собираюсь распараллелить несколько выборок тоже.Распараллеливание внутри распараллеливания ... звучит как отличный способ разбить кластер.Я знаю, как это сделать (и написать этот код, и разбить кластер).Мне нужна помощь, чтобы ускорить фактическую функцию.25 миллионов строк все еще занимает много времени для обработки с использованием моей текущей функции.Любые идеи очень приветствуются.Пожалуйста, измените мою функцию или порекомендуйте новый подход - все идеи приветствуются.Я не знаю о более быстрых методах, кроме добавления большего количества лошадиных сил.