2016-05-02 14 views
-1

RcppArmadilloに関する非常に簡単な質問です。ベクトルをスカラで掛けようとすると、構文の小さな変化に応じて異なる結果が得られます。RcppArmadilloとC++部門の問題

アイデア?

// [[Rcpp::depends("RcppArmadillo")]] 
// [[Rcpp::export]] 
arma::vec funtemp(arma::vec x)    
{ 
    // return(x/10); // this works 
    // return((1/10)*x); // this does not work 
    return(x*(1/10)); // this does not work 
} 
+1

@Coatlessがここに彼の時間と非常に寛大でした。基本的には、あるC/C++プログラマが遭遇するすべての初心者問題(迷惑ではありませんが、やむを得ない)のために落ちました。これは、RcppまたはArmadillo自体とは何も関係がありません。 –

答えて

2

ああ、C++での古き良きintegerdouble分割問題。我々が開始する前に、次の点に注意してください

#include <RcppArmadillo.h> 

// [[Rcpp::depends("RcppArmadillo")]] 

// [[Rcpp::export]] 
arma::vec funtemp_one(arma::vec x) 
{ 
    return(x/10); // this works 
} 

// [[Rcpp::export]] 
arma::vec funtemp_two(arma::vec x) 
{ 
    return((1/10)*x); // this does not work 
} 

// [[Rcpp::export]] 
arma::vec funtemp_three(arma::vec x) 
{ 
    return(x*(1/10)); // this does not work 
} 

したがって、ときに我々:arma::vec

はのは、別にあなたの機能を見てみましょう...デフォルトで1/10はすべてintのあるdouble110、ありますあなたの問題を介して実行我々が得る:後で機能で

> funtemp_one(1) 
    [,1] 
[1,] 0.1 

> funtemp_two(1) 
    [,1] 
[1,] 0 

> funtemp_three(1) 
    [,1] 
[1,] 0 

(例えば1/10)、使用されている210はintベースの除算です。その結果、2 intが入力され、1 intが返されます。結果が割り切れない場合は、整数スコープの外にあるゼロが返されます。

doubleを返すdouble型を使用するには、intの少なくとも1つを明示的にdoubleにキャストする必要があります。これは、arma::vecの構造のためにdouble/intがあるため、最初のケースではデフォルトで発生します。 1. intまたは2で明示的double(int)

例でdoubleとして値をキャストした後.0を使用する:第二及び第三のケースは、2つの方法で対処することができるint/int構造を有します

// [[Rcpp::export]] 
arma::vec funtemp_four(arma::vec x) 
{ 
    return(x*(1/10.0)); // this works 
} 

// [[Rcpp::export]] 
arma::vec funtemp_five(arma::vec x) 
{ 
    return(x*(1/double(10))); // this works 
} 

は、あなたが期待するもの与える:

> funtemp_four(1) 
    [,1] 
[1,] 0.1 

> funtemp_five(1) 
    [,1] 
[1,] 0.1