2016-01-06 474 views
1

我需要合併大型列表(aprox 15個數據幀[16000x6])。每個數據幀有2個id列"A""B"加上4列信息。將大型數據幀列表合併到一個數據幀中按列

我想要前兩個("A""B"加上一個數據幀中的15 * 4列)。

我在另一個問題發現這一點:

Reduce(function(x,y) merge(x,y,by="your tag here"),your_list_here) 

然而,這,死機我的機器給這個錯誤,因爲它需要太多RAM

In make.unique(as.character(rows)) : 
    Reached total allocation of 4060Mb: see help(memory.size) 
(僅使用3個DFS列表!)

我相信肯定會有更好的策略,我從dplyr包開始使用bind_cols,它讓我真的快速複製A和B列的數據幀。也許刪除這些列,保留前兩個是更好的方法。

我提供你一個小玩具列表(減少(...)的策略在這裏工作,但我需要另一種解決方案)

dput(mylist) 
structure(list(df1 = structure(list(A = c(1, 1, 2, 2, 3, 3), 
    B = c("Q", "Q", "Q", "P", "P", "P"), x1 = c(0.45840139570646, 
    0.0418491987511516, 0.798411589581519, 0.898478724062443, 
    0.064307059859857, 0.174364002654329), x2 = c(0.676136856665835, 
    0.494200984947383, 0.534940708894283, 0.220597118837759, 
    0.480761741055176, 0.0230771545320749)), .Names = c("A", 
"B", "x1", "x2"), row.names = c(NA, -6L), class = "data.frame"), 
    df2 = structure(list(A = c(1, 1, 2, 2, 3, 3), B = c("Q", 
    "Q", "Q", "P", "P", "P"), x1 = c(0.45840139570646, 0.0418491987511516, 
    0.798411589581519, 0.898478724062443, 0.064307059859857, 
    0.174364002654329), x2 = c(0.676136856665835, 0.494200984947383, 
    0.534940708894283, 0.220597118837759, 0.480761741055176, 
    0.0230771545320749)), .Names = c("A", "B", "x1", "x2"), row.names = c(NA, 
    -6L), class = "data.frame"), df3 = structure(list(A = c(1, 
    1, 2, 2, 3, 3), B = c("Q", "Q", "Q", "P", "P", "P"), x1 = c(0.45840139570646, 
    0.0418491987511516, 0.798411589581519, 0.898478724062443, 
    0.064307059859857, 0.174364002654329), x2 = c(0.676136856665835, 
    0.494200984947383, 0.534940708894283, 0.220597118837759, 
    0.480761741055176, 0.0230771545320749)), .Names = c("A", 
    "B", "x1", "x2"), row.names = c(NA, -6L), class = "data.frame")), .Names = c("df1", 
"df2", "df3")) 
+0

你能解釋一點點/顯示一些代碼嗎?我如何將15個dfs「存儲」在一個循環中以便合併工作?我想到拆分和合並,但又一次,我需要「某處」來放置這些dfs –

+0

你期望重複鍵發生了什麼?我懷疑這是什麼炸燬你的電腦。 「1 Q」有兩個條目,「3 P」有兩個條目。你真的只是想要綁定這些數據集嗎? – Zelazny7

+0

@ Zelazny7是的,我確定我想通過id列進行cbind +合併。記住我每DF有16000行,我寧願有一個16000 * 62比一個巨大的高DF。此外,後來我有很多基於列的代碼,許多函數會使用這些id colums並修改我不想再次編碼的其他列。我最初做的是手動子集,但我現在需要做得更好。 –

回答

2

基於註釋說明你要在16,000 X 62 data.frame。 ..

首先cbind非ID列:

tmp <- do.call(cbind, lapply(mylist, function(x) x[,-(1:2)])) 

然後加 「A」 和 「B」

final <- cbind(mylist[[1]][,1:2], tmp) 

沒有需要合併,只是巴掌data.frames一起

> final 
    A B  df1.x1  df1.x2  df2.x1  df2.x2  df3.x1  df3.x2 
1 1 Q 0.45840140 0.67613686 0.45840140 0.67613686 0.45840140 0.67613686 
2 1 Q 0.04184920 0.49420098 0.04184920 0.49420098 0.04184920 0.49420098 
3 2 Q 0.79841159 0.53494071 0.79841159 0.53494071 0.79841159 0.53494071 
4 2 P 0.89847872 0.22059712 0.89847872 0.22059712 0.89847872 0.22059712 
5 3 P 0.06430706 0.48076174 0.06430706 0.48076174 0.06430706 0.48076174 
6 3 P 0.17436400 0.02307715 0.17436400 0.02307715 0.17436400 0.02307715 
+0

OP說每個data.frame有16,000行。如果存在重複的ID,Reduce/merge會在最終輸出中產生一個包含16,000行以上的data.frame。 OP還在評論中指出,最終尺寸應該是16,000 x 62. – Zelazny7

3

對於cbind -ing的dataframes你可以這樣做:

L <- mylist[[1]] 
for (i in 2:length(mylist)) L <- cbind(L, mylist[[i]][-(1:2)]) 

對於merge -ing(如所示前者(但是錯誤的)期望的輸出爲例):

L <- mylist[[1]] 
for (i in 2:length(mylist)) L <- merge(L, mylist[[i]], by=c("A", "B")) 

在情況爲merge-我認爲內存的需求來自數據幀之間的m:n連接。這不能通過合併的另一個過程來解決。

+0

我喜歡這種方法,如果「A」和「B」相等,我懷疑合併檢查?如果不是,則會產生錯誤 –