向量化(非循环)解决方案返回错误的结果(带有for循环的解决方案返回正确的结果)

时间:2014-05-13 16:02:42

标签: r for-loop

我有理论上相同的解决方案,一个是矢量化解决方案,另一个是for-loop。但矢量化解决方案返回错误的结果,我想了解原因。解决方案的逻辑很简单:需要用向量中的先前非NA值替换NA。

# vectorized
f1 <- function(x) {
    idx <- which(is.na(x))
    x[idx] <- x[ifelse(idx > 1, idx - 1, 1)]
    x
}

# non-vectorized
f2 <- function(x) {
    for (i in 2:length(x)) {
        if (is.na(x[i]) && !is.na(x[i - 1])) {
            x[i] <- x[i - 1]
        }
    }
    x
}

v <- c(NA,NA,1,2,3,NA,NA,6,7)
f1(v)
# [1] NA NA  1  2  3  3 NA  6  7
f2(v)
# [1] NA NA  1  2  3  3  3  6  7

2 个答案:

答案 0 :(得分:4)

两段代码不同。

  • 第一个用前一个元素替换NA,如果这个元素不是NA。
  • 如果第二个元素不是NA,则第二个元素将NA替换为前一个元素,但前一个元素可能是之前NA替换的结果。

哪一个是正确的,取决于你。第二种行为更难以矢量化,但有一些已经实现的函数,如zoo::na.locf

或者,如果您只想使用基础包,可以查看this answer

答案 1 :(得分:3)

这两种解决方案并不相同。第一个功能就像:

f2_as_f1 <- function(x) {
    y <- x # a copy of x
    for (i in 2:length(x)) {
        if (is.na(y[i])) {
            x[i] <- y[i - 1]
        }
    }
    x
}

请注意y向量的用法。