big64 - NA矢量上的sum()产生奇数结果

时间:2015-02-13 05:34:23

标签: r bit64

使用big64包时,将NAs的向量与另一个整数向量相加会产生不准确的结果。根据{{​​1}}向量是第一个还是最后一个求和,结果将分别为NA或正确答案的两倍。

请注意,将0向量转换为integer64将会消除此问题。

然而,当用其他小值代替y进行试验时,结果非常奇怪。 例如:

NA

有关正在发生的事情的任何想法?

示例:

40 + 35 = 75    but
35 + 40 = 80

library(bit64) x <- as.integer64(c(20, 20)) y <- as.integer64(c(NA, NA)) sum(y, x, na.rm=TRUE) # integer64 # [1] 80 # <~~~ Twice the correct value sum(x, y, na.rm=TRUE) # integer64 # [1] 0 # <~~~~ Incorrect 0. Should be 40. ## Removing the NAs does not help. y <- y[!is.na(y)] ## A vector of 0's gives the same issue y <- as.integer64(c(0, 0)) ## Same results sum(y, x, na.rm=TRUE) # integer64 # [1] 80 sum(x, y, na.rm=TRUE) # integer64 # [1] 0 ## Converting to numeric does away with the issue (but is not a viable workaround, for obvious reasons) y <- as.numeric(y) sum(y, x, na.rm=TRUE) # [1] 1.97626e-322 sum.integer64(y, x, na.rm=TRUE) # integer64 # [1] 40 sum(x, y, na.rm=TRUE) # integer64 # [1] 40 一个值,结果也非常不合适

y

1 个答案:

答案 0 :(得分:2)

不是答案,而是探索。希望它可以帮助你。

来自sum.integer64包的bit64功能:

function (..., na.rm = FALSE) 
{
    l <- list(...)
    ret <- double(1)
    if (length(l) == 1) {
        .Call("sum_integer64", l[[1]], na.rm, ret)
        oldClass(ret) <- "integer64"
        ret
    }
    else {
        ret <- sapply(l, function(e) {
            if (is.integer64(e)) {
                .Call("sum_integer64", e, na.rm, ret)
                ret
            }
            else {
                as.integer64(sum(e, na.rm = na.rm))
            }
        })
        oldClass(ret) <- "integer64"
        sum(ret, na.rm = na.rm)
    }
}

以下是您的示例:

library(bit64)
x <- as.integer64(c(20, 20))
y <- as.integer64(c(NA, NA))

na.rm <- TRUE
l <- list(y, x)
ret <- double(1)
ret
#[1] 0

# We use the sapply function as in the function:
ret <- sapply(l, function(e) { .Call("sum_integer64", e, na.rm, ret) })
oldClass(ret) <- "integer64"
ret
#integer64
#[1] 40 40      <-- twice the value "40"
sum(ret, na.rm = na.rm)
# integer64
#[1] 80         <-- twice the expected value, as you said

这里我们为每个向量分解计算:

ret <- double(1)
ret2 <- NULL
ret2[1] <- .Call("sum_integer64", y, na.rm, ret)
ret2[2] <- .Call("sum_integer64", x, na.rm, ret)
oldClass(ret2) <- "integer64"
ret2
#integer64
#[1] 0  40      <-- only once the value "40", and "0" because of NaNs
sum(ret2, na.rm = na.rm)
#integer64
#[1] 40         <- expected value