0
我必须使用有时返回NULL的函数中的值填充向量(然后data.table)。这个例子说明了什么不顺心:如何保持向量长度和位置,尽管为NULL
library(data.table)
createNull1 <- function() { # I do not have access to the inside of this function
if ((i/2)%%1==0) { return("ABC") } else return(NULL)
}
createNull2 <- function() { # I do not have access to the inside of this function
if ((i/2)%%1==0) { return(NULL) } else return("XYZ")
}
my.data.table <- NULL
system.time(for (i in 1:10000) {
my.vector <- c(createNull1(),
createNull2(),
createNull1(),
createNull2(),
createNull1())
my.data.table <- rbind(my.data.table, data.table(my.vector))
})
产生的my.data.table有2列,但应该有5.这是为什么:
i <- 1
my.vector <- c(NULL, "ABC", NULL. "ABC", NULL) # But 2 resulting elements, not 5
i <- 2
my.vector <- c("XYZ", NULL, "XYZ", NULL, "XYZ") # But 3 resulting elements, not 5
我不能编辑的功能,因此该解决方案必须在for循环中找到。
我需要这样做几百万次,所以速度很重要。下面的代码解决了这个问题...
my.data.table <- NULL
system.time(for (i in 1:10000) {
my.vector <- c(if (is.null(createNull1())) NA else createNull1(),
if (is.null(createNull2())) NA else createNull2(),
if (is.null(createNull1())) NA else createNull1(),
if (is.null(createNull2())) NA else createNull2(),
if (is.null(createNull1())) NA else createNull1())
my.data.table <- rbind(my.data.table, data.table(my.vector))
})
...但是速度是两倍以上。
如何更快地创建my.data.table?
为什么你不能编辑功能?无论如何,你的代码很慢,因为你在循环中生成一个对象(阅读[The R Inferno](http://www.burns-stat.com/pages/Tutor/R_inferno.pdf))。它看起来很痛苦,因为你用data.table标记(但实际上不创建data.table)。如果你必须使用'for'循环(为什么?),至少要预先分配矩阵并用子集赋值。 – Roland
是否有你必须使用'NULL'和'NA'的理由? – hrbrmstr
函数来自比我理解的更先进的包。是的,我错过了my.vector周围的data.table()(例如不是真正的代码)。 – Chris