是否有某种方法可以使R对向量和其他序列数据结构使用从零开始的索引,如下所述,例如在C和python中。
我们有一些代码可以在C中进行一些数值处理,我们正在考虑将其移植到R中以利用其先进的统计功能,但是(根据我对谷歌搜索后的理解)缺少基于零的索引使这项工作有些困难更加困难。
我想展开辛寅的回答。可以定义新的类(如zero-based_vector
)、[
该类的方法,然后将该类分配给目标向量的属性。
# define new method for our custom class
index1 <- .Primitive('[')
`[.zero-based_vector` <- function(v, i) index1(as.vector(v), i+1)
x <- letters
# make `x` a zero-bazed_vector
class(x) <- c("zero-based_vector", class(x))
# it works!
x[0:3]
# [1] "a" "b" "c" "d"
Run Code Online (Sandbox Code Playgroud)
顺便说一句,没有任何东西会被破坏,因为我们不会覆盖.Primitive('[')
TL; DR:只是不要这样做!
我认为从零/一开始的索引并不是将C代码移植到R的主要障碍。但是,如果您确实认为有必要这样做,则可以覆盖.Primitive('[')
函数,从而更改C的行为。 R中的索引/子集。
# rename the original `[`
> index1 <- .Primitive('[')
# WICKED!: override `[`.
> `[` <- function(v, i) index1(v, i+1)
> x <- 1:5
> x[0]
[1] 1
> x[1]
[1] 2
> x[0:2]
[1] 1 2 3
Run Code Online (Sandbox Code Playgroud)
但是,这可能非常危险,因为您更改了基本索引行为,并且可能对所有利用子集和索引的库和函数造成意外的级联效果。
例如,由于子集和索引可以接受其他类型的数据作为选择器(例如布尔矢量),并且简单的覆盖函数没有考虑到这一点,因此您可能会遇到非常奇怪的行为:
> x[x > 2] # x > 2 returns a boolean vector, and by + 1, you convert
# boolean FALSE/TRUE to numeric 0/1
[1] 1 1 2 2 2
Run Code Online (Sandbox Code Playgroud)
尽管可以通过修改覆盖功能解决此问题,但是您仍然可能遇到其他问题。
另一个例子:
> (idx <- which(x > 2)) # which() still gives you 1-based index
> x[idx]
[1] 4 5 NA
Run Code Online (Sandbox Code Playgroud)
您永远都不知道哪里可能出问题了。所以,别这样。