Repository navigation
Is it true that as.data.table() does a shallow copy? #3665
Description
Activity
Ok, it's probably not doing a shallow copy, since both functions get much slower for a larger table:
library(data.table) mtcars_big <- data.table(mtcars)[rep(1:32, each = 1e6), ] bench::mark( copy(mtcars_big), as.data.table(mtcars_big), check = FALSE )[1:6] #> Warning: Some expressions had a GC in every iteration; so filtering is #> disabled. #> # A tibble: 2 x 6 #> expression min mean median max `itr/sec` #> <chr> <bch:tm> <bch:tm> <bch:tm> <bch:tm> <dbl> #> 1 copy(mtcars_big) 2.75s 2.75s 2.75s 2.75s 0.363 #> 2 as.data.table(mtcars_big) 2.39s 2.39s 2.39s 2.39s 0.418
Created on 2019-06-26 by the reprex package (v0.2.1.9000)
But maybe
dt[TRUE, ]does?library(data.table) dt <- data.table(x = 1:3) dt2 <- dt[TRUE, ] dt[, y := 1] dt #> x y #> 1: 1 1 #> 2: 2 1 #> 3: 3 1 dt2 #> x #> 1: 1 #> 2: 2 #> 3: 3 mtcars_big <- data.table(mtcars)[rep(1:32, each = 1e6), ] bench::mark( copy(mtcars_big), mtcars_big[TRUE, ], check = FALSE )[1:6] #> Warning: Some expressions had a GC in every iteration; so filtering is #> disabled. #> # A tibble: 2 x 6 #> expression min mean median max `itr/sec` #> <chr> <bch:tm> <bch:tm> <bch:tm> <bch:tm> <dbl> #> 1 copy(mtcars_big) 2.7s 2.7s 2.7s 2.7s 0.370 #> 2 mtcars_big[TRUE, ] 80.3µs 304µs 109.1µs 291.2ms 3290.
Created on 2019-06-26 by the reprex package (v0.2.1.9000)
Regarding DT[TRUE] I think that is just a temporary option for shallow copy until shallow() is exported: #3214 (comment)
For the other operation you're doing (as.data.table on a data.table), the internals are written in R so there's no need to treat it as a black box:
> data.table:::as.data.table.data.table function (x, ...) { x = copy(x) setattr(x, "class", .resetclass(x, "data.table")) return(x) } <bytecode: 0x0000000010af4280> <environment: namespace:data.table>I usually use data.table::address to check if a copy is made (and, I guess there are analogues in pryr or base R).
The latter one does, see #3214
I guess I'm asking if
DT[TRUE]will continue to perform a shallow copy in the future, or it's seen as an undocumented feature that I shouldn't rely on. #3214 (comment) suggests I shouldn't rely on it.- addedby-referenceIssues related to by-reference/copying behaviorIssues related to by-reference/copying behavior
on Jul 15, 2025
It seems that
as.data.table(dt)creates a "shallow" copy of its input? The reprex below suggests it does, but is this something that I can rely on?Created on 2019-06-26 by the reprex package (v0.2.1.9000)