Rcpp:一个函数适用于 NumericVector,另一个需要将其视为标量
Rcpp: one function works on NumericVector, the other needs to treat it as scalar
我有两个用 Rcpp 编写的函数。
第一个函数 f
将 NumericVector 作为输入,returns 将 NumericVector 作为输出。但通常,f
意味着被视为标量函数。当我从 R 调用它时,没关系,因为 R 无论如何都会将任何标量视为向量,所以我不必为此操心。我可以将 f
用作标量或矢量函数,例如f(1)
和 f(c(1,2,3,4)
都有效。
- 问题 1:这是个坏主意吗?我应该制作两个独立的函数,一个是标量函数,一个是向量化函数吗?例如,当我使用标量输入而不是向量从 R 调用
f
时,是否存在一些不需要的开销?
第二个函数g
需要将f
纯粹用作标量函数。这会导致问题,因为我在定义 g
时需要从 Rcpp 调用 f
。现在我不能通过调用 f(x
) 来将它用作标量函数双 x。
我尝试从 g
:
的定义中做类似的事情
NumericVector x = NumericVector::create(value); //create vector of length 1
f(x) //use f(x) as scalar
但是代码的计时时间长得离谱(因为函数 g
需要多次执行上述操作)。
- 问题 2:有没有一种方法可以更快地将
f
视为标量函数,就像我在 R 中一样?
我目前的解决方案是按照我在问题 1 中提出的要求进行操作:创建另一个 f
标量函数,然后从 g
调用那个函数,以便在 g
中我们只是说
alternative_f(x) //use alternative f as scalar
您可以将标量代码分解为一个单独的(内联)函数,并从 f
(使用 std::transform
)和 g
(+ 附加逻辑)调用它。简化示例:
#include <Rcpp.h>
inline double f_impl (double x) {
return x * 2;
}
// [[Rcpp::export]]
double g (double x) {
return f_impl(x) + 2;
}
// [[Rcpp::export]]
Rcpp::NumericVector f (Rcpp::NumericVector x) {
Rcpp::NumericVector y(Rcpp::no_init(x.length()));
std::transform(x.begin(), x.end(), y.begin(), f_impl);
return y;
}
我有两个用 Rcpp 编写的函数。
第一个函数 f
将 NumericVector 作为输入,returns 将 NumericVector 作为输出。但通常,f
意味着被视为标量函数。当我从 R 调用它时,没关系,因为 R 无论如何都会将任何标量视为向量,所以我不必为此操心。我可以将 f
用作标量或矢量函数,例如f(1)
和 f(c(1,2,3,4)
都有效。
- 问题 1:这是个坏主意吗?我应该制作两个独立的函数,一个是标量函数,一个是向量化函数吗?例如,当我使用标量输入而不是向量从 R 调用
f
时,是否存在一些不需要的开销?
第二个函数g
需要将f
纯粹用作标量函数。这会导致问题,因为我在定义 g
时需要从 Rcpp 调用 f
。现在我不能通过调用 f(x
) 来将它用作标量函数双 x。
我尝试从 g
:
NumericVector x = NumericVector::create(value); //create vector of length 1
f(x) //use f(x) as scalar
但是代码的计时时间长得离谱(因为函数 g
需要多次执行上述操作)。
- 问题 2:有没有一种方法可以更快地将
f
视为标量函数,就像我在 R 中一样?
我目前的解决方案是按照我在问题 1 中提出的要求进行操作:创建另一个 f
标量函数,然后从 g
调用那个函数,以便在 g
中我们只是说
alternative_f(x) //use alternative f as scalar
您可以将标量代码分解为一个单独的(内联)函数,并从 f
(使用 std::transform
)和 g
(+ 附加逻辑)调用它。简化示例:
#include <Rcpp.h>
inline double f_impl (double x) {
return x * 2;
}
// [[Rcpp::export]]
double g (double x) {
return f_impl(x) + 2;
}
// [[Rcpp::export]]
Rcpp::NumericVector f (Rcpp::NumericVector x) {
Rcpp::NumericVector y(Rcpp::no_init(x.length()));
std::transform(x.begin(), x.end(), y.begin(), f_impl);
return y;
}