[datatable-help] Help using a quoted eval statement
Griffith Rees
griffith.rees at sociology.ox.ac.uk
Sun Jul 24 19:10:00 CEST 2011
Hi,
Sorry if there is a straightforward answer, been trying various
solutions and I can't quite get what I want. What I need to do is find
a weighted mean of a grouped set for most of the variables in a
data.table. The sort of thing I wish I could write is:
dt[,sum(.SD[9:20]*Population/sum(Population)), by=ExchangeArea]
where [9:28] is the subset of the variables of data.table dt that I
want a weighted sum of. Ideally, the resultant data.table would label
the columns the same as those variables. Obviously this doesn't work,
so I've tried to find a way to iterate over a list of variables.
Here's what I hoped would work:
dt.final <- dt #copy original data.table
l <- names(dt)
l <- l[9:28] #Get the right names
wtavg <- function(variable) {dt.final <-
dt.final[dt.final[,variable=sum(variable*Population/sum(Population)),by=ExchangeArea]]}
lappy(l,wtavg)
That errored, so I tried using the eval(quote()) idiom from the documentation:
wtavg.expression <-
function(variable){paste(variable,"=sum(",variable,"*Population/sum(Population))",
sep="")}
However, trying to just get one column out gives me this error:
wtavg <- function(variable)
{dt[,eval(quote(wtavg.expression(variable))),by=ExchangeArea]}
wtavg('Technicians')
ExchangeArea V1
[1,] 23826 Technicians=sum(Technicians*Population/sum(Population))
[2,] 23827 Technicians=sum(Technicians*Population/sum(Population))
[3,] 23828 Technicians=sum(Technicians*Population/sum(Population))
[4,] 23829 Technicians=sum(Technicians*Population/sum(Population))
[5,] 23830 Technicians=sum(Technicians*Population/sum(Population))
[6,] 23831 Technicians=sum(Technicians*Population/sum(Population))
[7,] 23832 Technicians=sum(Technicians*Population/sum(Population))
[8,] 23833 Technicians=sum(Technicians*Population/sum(Population))
[9,] 23834 Technicians=sum(Technicians*Population/sum(Population))
[10,] 23835 Technicians=sum(Technicians*Population/sum(Population))
First 10 rows of 16051 printed.
Now it appears that shouldn't work because I'm passing a string to
quote() rather than an expression. However, I haven't been able to
find a function that will do what I want. I've tried various
combinations of:
expresssion()
substitute()
parse()
eval()
quote()
and most of them give me errors. I hope it's clear what I'm trying to
do. I do realise that I could write a giant expression by hand, but
part of me thinks there should be a better way. Any suggestions would
be helpful, thanks very much.
--
Griffith Rees
Sociology DPhil Candidate
Oxford University
CABDyN Complexity Centre
http://www.cabdyn.ox.ac.uk
More information about the datatable-help
mailing list