2013-05-16 12 views
6

Nell'argomento j in data.table, esiste una sintassi che mi consenta di fare riferimento a variabili create in precedenza nella stessa dichiarazione j? Sto pensando a qualcosa come il costrutto di Lisp let*.Posso usare variabili appena create in `j` nello stesso argomento` j`?

library(data.table) 
set.seed(22) 
DT <- data.table(a = rep(1:5, each = 10), 
       b = sample(c(0,1), 50, rep = TRUE)) 

DT[ , 
    list(attempts = .N, 
     successes = sum(b), 
     rate = successes/attempts), 
    by = a] 

Questo si traduce in

# Error in `[.data.table`(DT, , list(attempts = .N, successes = sum(b), : 
# object 'successes' not found 

capisco perché, ma c'è un modo diverso per ottenere questo risultato nella stessa j?

+1

possibile duplicato del [colonna appena aggiunta nel 'j' di data.table dovrebbe essere disponibile nel campo di applicazione] (http://stackoverflow.com/questions/16510915/newly-added-column-in-j-of-data-table-should-be-available-in-the-scope) –

+1

@RicardoSaporta - Si tratta di un duplicato di questo: [ Come posso valutare (o creare) una colonna al volo in data.table in r] (http://stackoverflow.com/que stions/15712858/how-can-i-evaluate-or-create-an-on-the-fly-column-in-data-table-in-r/15713753 # comment22337886_15713753);) Sembra essere un desiderio comune tra i dati .table per gli utenti. –

+0

@ JoshO'Brien, è grandioso! Forse possiamo unirli tutti? Bella osservazione però. Forse dovremmo mettere qualcosa nelle DT FAQ su questo –

risposta

7

questo farà il trucco:

DT[ , { 
    list(attempts = attempts <- .N, 
     successes = successes <- sum(b), 
     rate = successes/attempts) 
    }, by = a] 
# a attempts successes rate 
# 1: 1  10   5 0.5 
# 2: 2  10   6 0.6 
# 3: 3  10   3 0.3 
# 4: 4  10   5 0.5 
# 5: 5  10   5 0.5 

FWIW, this closely related data.table feature request renderebbe possibile +/- la sintassi utilizzata nella sua interrogazione. Citando dalla pagina collegata:

Sommario:

iterativo RHS di := (e `:=`(...)), e multipla := all'interno j = {...} sintassi

Descrizione dettagliata

esempio DT[, `:=`(m1 = mean(a), m2 = sd(a), s = m1/m2), by = group]

dove s può utilizzare i nomi di ls precedenti (utilizzando la parola 'iterativo' tenta di comunicare ciò).

+0

+1 per tirare il FR –

4

Prova a modificare:

DT[, 
    {successes = sum(b); 
    attempts = .N; 
    list(attempts = attempts, 
     successes = successes, 
     rate = successes/attempts) 
    }, 
    by = a] 

o

DT[, 
    list(attempts = .N, 
     successes = sum(b)), 
    by = a][, rate := successes/attempts]