2012-04-11 12 views
6

डेटाटेबल का उपयोग करना, जो स्तंभों के चयन में एक आंकड़े को "साफ़" करने का सबसे तेज़ तरीका होगा?डेटाटेबल्स और स्वीप फ़ंक्शन

(का काफी बड़ा संस्करण) डीटी

p <- 3 
DT <- data.table(id=c("A","B","C"),x1=c(10,20,30),x2=c(20,30,10)) 
DT.totals <- DT[, list(id,total = x1+x2) ] 

के साथ शुरू मैं लक्ष्य कॉलम (2: पी) का अनुक्रमण द्वारा निम्नलिखित data.table परिणाम को प्राप्त करना चाहते हैं क्रम में कुंजी को छोड़ने के लिए:

id x1 x2 
[1,] A 0.33 0.67 
[2,] B 0.40 0.60 
[3,] C 0.75 0.25 

उत्तर

4

मुझे विश्वास है कि कुछ निम्नलिखित (जो अपेक्षाकृत नया set() समारोह उपयोग करता है) के पास तेज हो जाएगा:

DT <- data.table(id = c("A","B","C"), x1 = c(10,20,30), x2 = c(20,30,10)) 
total <- DT[ , x1 + x2] 

rr <- seq_len(nrow(DT)) 
for(j in 2:3) set(DT, rr, j, DT[[j]]/total) 
DT 
#  id  x1  x2 
# [1,] A 0.3333333 0.6666667 
# [2,] B 0.4000000 0.6000000 
# [3,] C 0.7500000 0.2500000 

Fwiw, कॉल set() निम्नलिखित रूप लेता करने के लिए:

# set(x, i, j, value), where: 
#  x is a data.table 
#  i contains row indices 
#  j contains column indices 
#  value is the value to be assigned into the specified cells 

अन्य समाधान की तुलना में इस के सापेक्ष गति के बारे में मेरे संदेह,, data.table's NEWS file से इस मार्ग पर आधारित है परिवर्तन पर अनुभाग में, संस्करण 1.8.0 में:

o New function set(DT,i,j,value) allows fast assignment to elements 
    of DT. Similar to := but avoids the overhead of [.data.table, so is 
    much faster inside a loop. Less flexible than :=, but as flexible 
    as matrix subassignment. Similar in spirit to setnames(), setcolorder(), 
    setkey() and setattr(); i.e., assigns by reference with no copy at all. 

     M = matrix(1,nrow=100000,ncol=100) 
     DF = as.data.frame(M) 
     DT = as.data.table(M) 
     system.time(for (i in 1:1000) DF[i,1L] <- i) # 591.000s 
     system.time(for (i in 1:1000) DT[i,V1:=i])  # 1.158s 
     system.time(for (i in 1:1000) M[i,1L] <- i) # 0.016s 
     system.time(for (i in 1:1000) set(DT,i,1L,i)) # 0.027s 
+0

जवाब के लिए धन्यवाद। मैंने data.table 1.8.0 में अपग्रेड किया है, और सफलतापूर्वक उपरोक्त परीक्षण कोड चलाया है। जब मैं संख्यात्मक और denominators डेटा.tables से पूर्णांक कॉलम हैं, तो मुझे दोगुना करने के बारे में एक विस्तृत चेतावनी मिलती है (यहां फिट नहीं होगी)। मैं इस प्रभाव को उस प्रश्न में संपादित करूंगा। –

+0

मुझे आज संपादन के साथ कठिन समय है: कोई लाइन फीड नहीं। वैसे भी, यहां कोड है: के लिए (जे 2: पी) { सेट (डीटी, आलू, जे, डीटी [[जे]]/denom [[2]]) } और दोनों डीटी और denom के लिए, कॉलम 2 के लिए पी पूर्णांक हैं। मुझे प्राप्त चेतावनी –

+0

है "चेतावनी संदेश: सेट में (डीटी, आलू, जे, डीटी [[जे]]/denom [[2]]): कॉलम के प्रकार से मेल खाने के लिए 'पूर्णांक' के लिए 'डबल' आरएचएस को 'पूर्णांक' ; कटा हुआ परिशुद्धता हो सकती है। या तो लक्ष्य कॉलम को पहले 'डबल' में बदलें (एक नई 'डबल' वेक्टर लंबाई 16863 (संपूर्ण तालिका के नाक) बनाकर और इसे असाइन करें; यानी 'प्रतिस्थापन' कॉलम), या आरएचएस को 'पूर्णांक' '(उदाहरण के लिए 1 एल, एनए_ [असली | पूर्णांक] _, जैसा। *, आदि) अपना इरादा स्पष्ट और गति के लिए। या, जब आप तालिका बनाते हैं और इसके साथ चिपके रहते हैं तो स्तंभ प्रकार को सही तरीके से ऊपर सेट करें। " –

संबंधित मुद्दे