Я надеюсь получить совет по управлению большими наборами комбинаций в R.
Я аспирант в области селекции растений и пытаюсь вычислить наивысшие средние значения потомства различных комбинаций 40 родителей в популяции растений. Я начинаю с создания матрицы, содержащей значения, полученные путем скрещивания этих родителей:
# fake data
B <- matrix (data=runif(1600, 1.0, 5.0),ncol=40,nrow=40)
diag(B) <- diag(B) - 1 # diagonals are when plants are crossed to themselves and suffer inbreeding depression
Я делаю это, находя среднее значение подмножества матрицы ("perse.hybrid"), содержащей различные комбинации родителей:
SubsetWright <- function (perse.hybrid, subset) {
return (mean(perse.hybrid[subset,subset]))
}
В идеале я хотел бы найти значения потомства для всех комбинаций 40 родителей, но немного более реалистично я хотел бы найти значения для комбинации от 2 до 11 родителей. Это около 3,5 миллиардов комбинаций.
Я работал над ускорением этого, а также над управлением памятью. Чтобы ускорить его, я настроил его на параллельный запуск задач в кластере Amazon EC2 (обычно это 3 машины m4.10xlarge). Чтобы решить проблему с памятью, я попытался сохранить данные в big.matrix. Тем не менее, я, кажется, натыкаюсь на combn. Обычно, когда я добираюсь до 40, выбираю 8, он вылетает. Смотря htop, я считаю, что это из-за использования памяти.
Я начинающий пользователь R и не совсем понимаю, как в R управляется память. Кажется, я мог бы получить эти ограничения, если бы каким-то образом разделил функцию combn, что могло бы позволить мне запускать ее параллельно и избежать пределы памяти. Или, возможно, есть способ заполнить big.matrix всеми комбинациями без использования combn. У кого-нибудь есть какие-либо стратегии, чтобы предложить? Код ниже. Большое спасибо!
#' Test all combinations of parents to find set of offspring with highest estimated mean.
#'
#' @param perse.hybrid A matrix of offspring values, with row[i]=col[j]=parent ID
#' @param min The minimum number of parents to test combinations of
#' @param max The maximum number of parents to test combinations of
#' @param rows Number of rows of top combinations to return, default is to return all rows
#' @param cl cluster to use
#' @return A big.matrix with parent combinations and predicted average offspring values
TestSyn <- function (perse.hybrid, min, max, rows="all", cl) {
clusterExport(cl, list("SubsetWright"))
total <- sum(apply(X=array(min:max),MARGIN=1,FUN=choose,n=nrow(perse.hybrid)))
n <- nrow(perse.hybrid)
start <- 1
stop <- choose(n,min)
syn.data <- big.matrix(nrow=total,ncol=max+1)
for (i in min:max)
{
#add inbred numbers to syn.data. This seems to be what crashes when i gets large (>7)
inbreds <- t(combnPrim(1:n,i))
syn.data[start:stop,1:i] <- inbreds
#add sythetic values to syn.data
syn.data[start:stop,max+1] <- parApply(cl=cl,X=inbreds,MARGIN=1,FUN=SubsetWright,perse.hybrid=perse.hybrid)
start <- stop + 1
stop <- start + choose(n,i+1) - 1
}
# sort by offspring average
mpermute(x=syn.data,cols=max+1,decreasing=TRUE)
if (rows == "all") rows <- nrow(syn.data)
return (syn.data[1:rows,])
}
РЕДАКТИРОВАТЬ:
При дальнейшем изучении кажется, что комбинаторика может быть частью решения. Сообщение Stackoverflow здесь: Создание очень большого матрица комбинаций строк с помощью combn() и пакета bigmemory
Я проведу некоторое тестирование, чтобы увидеть, держится ли это с большими числами.