Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Consistency in 'i' for integer and logical types #697

Closed
arunsrinivasan opened this issue Jun 16, 2014 · 3 comments · Fixed by #3589
Closed

Consistency in 'i' for integer and logical types #697

arunsrinivasan opened this issue Jun 16, 2014 · 3 comments · Fixed by #3589

Comments

@arunsrinivasan
Copy link
Member

@arunsrinivasan arunsrinivasan commented Jun 16, 2014

Currently, there is one small inconsistency in row-subset using integer and logical types:

require(data.table)
DT <- data.table(x=1:2, y=c(TRUE, FALSE))
v1 = 1L

i as integer:

DT[1L]
#    x    y
#1: 1 TRUE
DT[x]
# Error in eval(expr, envir, enclos) : object 'x' not found 
# Corrected the output here.. Thanks to @eddi.
DT[v1]
#    x    y
#1: 1 TRUE
DT[(x)]
#    x     y
#1: 1  TRUE
#2: 2 FALSE

The same happens for logical type as well.

The question is, can we get this indexing to work without the need for ( for cases where i is a column in DT instead of throwing the error?

Edit: Cleaned up noise and retained just the resolution.

@mattdowle
Copy link
Member

@mattdowle mattdowle commented Jun 17, 2014

FR #633 title says "and maybe . and .. prefixes to symbols". There I was thinking . and .. on the symbols themselves. We do that anyway ourselves (manually) right? So it's really just building it in.

ids = c("id1","id2")
DT[ids]     # uses ids in calling scope because i is a single variable name
             # on its own (rule in ?data.table).  Common usage now.
DT[ logicalCol == TRUE ]   # pretty clear,  but possible mistakes if logicalCol
               # isn't actually a column but is in calling scope
DT[ logicalCol ]     # 'not found' currently but better error could suggest : 
DT[ (logicalCol) ]   # currently what I do to make it not a single name
DT[ .logicalCol ]     # same, but error if no column is called "logicalCol"
         # even if it does exist in calling scope (more robust)
DT[ colA > ..value ]   # use 'value' in calling scope even if there's a column
                        # called "value".  We do this manually currently by
                        # defining ..value in calling scope.
DT[ .colA > .colB ]    # be explicit that colA and colB must be in DT
                        # otherwise error
DT[ colA > colB,  strict.scope=TRUE]  # same,  without needing . prefixes

strict.scope could be a global option as usual. All variables would have to be column names and the only way to get to calling scope would be to use the .. prefix. I seem to remember Hadley suggested something like this to us once.

. and .. are really just an extension of the i. and x. prefixes on variable names that we already have, similar to SQL prefixes and useful in join inherited scope.

@arunsrinivasan
Copy link
Member Author

@arunsrinivasan arunsrinivasan commented Jun 17, 2014

Okay, sounds good.

@MichaelChirico
Copy link
Member

@MichaelChirico MichaelChirico commented May 23, 2019

On current master, this is the error:

x is not found in calling scope and it is not a column of type logical. When the first argument inside DT[...] is a single symbol, data.table looks for it in calling scope.

For y we get:

DT[y]

y is not found in calling scope but it is a column of type logical. If you wish to select rows where that column is TRUE, either wrap the symbol with '()' or use ==TRUE to be clearest to readers of your code.

So, it seems we could at least make the error message a bit more consistent:

x is not found in calling scope but it is a column of type integer...

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants