2017-08-03 83 views
2

我有一個需要太長時間計算的腳本,我試圖將其執行過程並行化。在R中使用應用系列並行化用戶定義的函數

劇本基本上遍歷數據幀的每一行,並執行一些計算,如下圖所示:

my.df = data.frame(id=1:9,value=11:19) 

sumPrevious <- function(df,df.id){ 
    sum(df[df$id<=df.id,"value"]) 
} 

for(i in 1:nrow(my.df)){ 
    print(sumPrevious(my.df,my.df[i,"id"])) 
} 

我開始學會R中並行代碼,這就是爲什麼我首先要了解我怎麼可以用類似apply的函數來做到這一點(例如sapply,lapply,mapply)。

我嘗試過許多東西,但沒有到目前爲止的工作:

mapply(sumPrevious,my.df,my.df$id) # Error in df$id : $ operator is invalid for atomic vectors 
+1

'lapply','sapply','mapply'不會並行執行操作。他們連續運行一個功能。你想僅僅用'lapply'替換'for loop'還是你想並行運行你的代碼? – TUSHAr

+0

你爲此需要並行化似乎很奇怪?假設「my.df $ id」是排序的,你試圖實現的只是'cumsum(my.df $ value)'。 –

回答

3

使用parallel包中的R可以使用mclapply()功能。您需要稍微調整代碼才能使其並行運行。

library(parallel) 
my.df = data.frame(id=1:9,value=11:19) 

sumPrevious <- function(i,df){df.id = df$id[i] 
    sum(df[df$id<=df.id,"value"]) 
} 

mclapply(X = 1:nrow(my.df),FUN = sumPrevious,my.df,mc.preschedule = T,mc.cores = no.of.cores) 

該代碼將在您的機器上並行運行no.of.cores sumPrevious。

+1

太棒了!非常感謝 :) – Victor

1

嗯,這是很有趣的玩法。你那種需要像下面:

mapply(sumPrevious,list(my.df),my.df$id) 

供應,因爲第一輸入數據框,你必須定義一個給定的功能它是強麥認識到它如此:

sapply(my.df$id,function(x,y) sumPrevious(y,x),my.df) 

由於我們可以將第一個值設置爲數據框,因此我更喜歡這裏的mapply。但整個數據幀。這就是爲什麼你必須使用功能list

Map是一個mapply的包裝,因此只會以列表格式提供解決方案。嘗試一下。另外lapplysapply類似,只有sapply必須將結果簡化爲數組格式,而lapply會給出與列表相同的結果。

雖然看起來你想做的任何事情都可以簡單地通過cumsum函數完成。

cumsum(df$values) 
相關問題