2013-10-22 63 views
4

前段時間,我問了一個關於創建購物籃數據的問題。現在我想創建一個類似的data.frame,但基於第三個變量。不幸的是,我遇到了問題。上一個問題:Effecient way to create market basket matrix in R
@shadow和@ SimonO101給了我很好的答案,但是我無法正確改變他們的anwser。我有以下數據:基於第三變量(數值)的聯合表

Customer <- as.factor(c(1000001,1000001,1000001,1000001,1000001,1000001,1000002,1000002,1000002,1000003,1000003,1000003)) 
Product <- as.factor(c(100001,100001,100001,100004,100004,100002,100003,100003,100003,100002,100003,100008)) 
input <- data.frame(Customer,Product) 

我現在可以創建一個列聯表方式如下:

input_df <- as.data.frame.matrix(table(input)) 

但是我有我想作爲表輸出三分之一(數字)變量。

Number <- c(3,1,-4,1,1,1,1,1,1,1,1,1) 
input <- data.frame(Customer,Product,Number) 

現在代碼(當然,現在有3個變量)不再工作。我所查找的結果具有唯一的Customer作爲行名稱和唯一的Product作爲列名稱。並擁有數量價值(或0,如果不存在),這個數字可以由下式計算:

input_agg <- aggregate(Number ~ Customer + Product, data = input, sum) 

希望我的問題是清楚的,請評論,如果事情是不明確。

+0

+1再重複的例子。 –

+0

您是否能夠成功完成「聚合」步驟? – A5C1D2H2I1M1N2O1R2T1

回答

6

您可以使用xtabs爲:

R> xtabs(Number~Customer+Product, data=input) 

     Product 
Customer 100001 100002 100003 100004 100008 
    1000001  0  1  0  2  0 
    1000002  0  0  3  0  0 
    1000003  0  1  1  0  1 
+0

+1我總是忘記xtabs。好的回答, –

+0

@ SimonO101事實上,我剛剛發現它:-) – juba

+0

我認爲這不是一個效率問題,而是您的系統上有多少RAM。無論你用什麼方法來計算它,你總是會得到一個90000x2000的表格來存儲內存...... – juba

4

這類的問題是專爲reshape2::dcast ...

require(reshape2) 
# Too many rows so change to a data.table. 
dcast(input , Customer ~ Product , fun = sum , value.var = "Number") 
# Customer 100001 100002 100003 100004 100008 
#1 1000001  0  1  0  2  0 
#2 1000002  0  0  3  0  0 
#3 1000003  0  1  1  0  1 

最近,使用dcastdata.table對象的方法是由@Arun實施應對FR #2627。好東西。您將不得不使用開發版本1.8.11。此刻,它應該被用作dcast.data.table。這是因爲dcast不是S3通用的,而是在reshape2包中。也就是說,你可以這樣做:

require(reshape2) 
require(data.table) 
input <- data.table(input) 
dcast.data.table(input , Customer ~ Product , fun = sum , value.var = "Number") 
# Customer 100001 100002 100003 100004 100008 
# 1: 1000001  0  1  0  2  0 
# 2: 1000002  0  0  3  0  0 
# 3: 1000003  0  1  1  0  1 

這應該相當不錯的更大的數據應該比reshape2:::dcast快得多以及。


或者,你可以嘗試reshape:::cast版本,這可能會或可能不會崩潰......試試吧!

require(reshape) 
input <- data.table(input) 
cast(input , Customer ~ Product , fun = sum , value = .(Number)) 
+0

快速響應,確實有效。但是它會讓我的R會話直接崩潰。我更新了我的問題。 – Freddy

+0

@Freddy查看更新。使用'data.table'。 dcast方法已經爲此編寫。應該快速並避免崩潰你的電腦! –

+0

@Freddy,但有一個'data.table'而不是'data.frame'?這是一個重要的區別!另外,如果你不把輸出分配給一個變量,它會嘗試打印到控制檯,它可能會崩潰,所以試着複製/粘貼這個...'input < - data.table(input);輸出< - dcast(輸入,Customer〜Product,fun = sum,value.var =「Number」)' –