Rcpp和int64 NA值

问题描述 投票:2回答:1

如何在64位向量中将Rcpp的NA值传递给R?

我的第一个方法是:

// [[Rcpp::export]]                                     
Rcpp::NumericVector foo() {
  Rcpp::NumericVector res(2);

  int64_t val = 1234567890123456789;
  std::memcpy(&(res[0]), &(val), sizeof(double));
  res[1] = NA_REAL;

  res.attr("class") = "integer64";
  return res;
}

但是会产生

#> foo()
integer64
[1] 1234567890123456789 9218868437227407266

我需要得到

#> foo()
integer64
[1] 1234567890123456789 <NA>
r rcpp na bit64
1个回答
1
投票

好吧,我想我找到了答案...(虽然不漂亮,但是可以工作。)>

简短回答:
// [[Rcpp::export]]                                     
Rcpp::NumericVector foo() {
  Rcpp::NumericVector res(2);

  int64_t val = 1234567890123456789;
  std::memcpy(&(res[0]), &(val), sizeof(double));

  # This is the magic:
  int64_t v = 1ULL << 63;
  std::memcpy(&(res[1]), &(v), sizeof(double));

  res.attr("class") = "integer64";
  return res;
}

这导致

#> foo()
integer64
[1] 1234567890123456789 <NA>

更长的答案

检查bit64如何存储NA

# the last value is the max value of a 64 bit number
a <- bit64::as.integer64(c(1, 2, NA, 9223372036854775807))
a
#> integer64
#> [1] 1    2    <NA> <NA>
bit64::as.bitstring(a[3])
#> [1] "1000000000000000000000000000000000000000000000000000000000000000"
bit64::as.bitstring(a[4])
#> [1] "1000000000000000000000000000000000000000000000000000000000000000"

reprex package(v0.3.0)在2020-04-23创建

我们看到它是一个10000...。可以用Rcppint64_t val = 1ULL << 63;中重新创建。使用memcpy()而不是使用=进行简单分配,可以确保没有位被更改!

© www.soinside.com 2019 - 2024. All rights reserved.