[Rcpp-devel] function modifying it self its argument
Matt D.
matdzb at gmail.com
Thu Feb 26 18:35:52 CET 2015
On 2/26/2015 16:37, Pierre GLOAGUEN wrote:
> Thanks, it works!
> I'm not familiar with C++, is it necessary to always use such a
> function in C++ or is it because of R/C++ interface?
Hi Pierre!
You're witnessing yet another fascinating difference between (usual in
the world of C++) value semantics and (not that usual in the world of
C++) reference semantics:
Compare the difference in behavior of `vector_reference` (using
`Rcpp::NumericVector`) and `vector_value` (using `std::vector<double>`)
in the code attached below.
To make things clear: no, in C++ you're not (not by default and not in
the standard world) supposed to care about (nor use) a function such as
`clone` -- this is idiomatic in programming languages with reference
semantics, like Java: https://en.wikipedia.org/wiki/Clone_%28Java_method%29
If this makes you feel better: If you're coming from C++ your
expectations are perfectly reasonable and this is how any well-designed
(as in: not violating the POLS) C++ library (including the C++ standard
library) will behave by default.
Which incidentally brings me to the advice I usually give in these
situations: unless you're absolutely dependent on the "features" of
`Rcpp::NumericVector` just forget about it and replace all uses with the
standard container `std::vector<double>`.
// Arguably, NumericVector's POLS violation -- as illustrated by the
numerous posts raising similar questions -- perhaps isn't necessarily
the optimal design choice?
Everything will behave just as you expect and as well-documented in the
usual places -- e.g., http://en.cppreference.com/w/cpp/container/vector
In contrast, `help.search("Rcpp::NumericVector")` happily announces "No
results found" at the moment -- and, as mentioned in another reply,
you're apparently expected to Google around to find methods for solving
problems you wouldn't even encounter otherwise.
As fun as it can be to learn-via-a-search-engine, if you don't find the
curiosities like the aforementioned reference-vs-value-semantics
differences _all_ _that_ fascinating, I think you may find yourself more
productive and better served by sticking to the standard containers :-)
HTH!
#include <Rcpp.h>
// [[Rcpp::export]]
Rcpp::NumericVector vector_reference(Rcpp::NumericVector input)
{
Rcpp::NumericVector output(input);
if (output.size() >= 1) output[0] = 123;
return output;
}
// [[Rcpp::export]]
std::vector<double> vector_value(const std::vector<double> & input)
{
std::vector<double> output(input);
if (output.size() >= 1) output[0] = 123;
return output;
}
/*** R
v = rep(1, 6)
vector_reference(v)
show(v)
v = rep(1, 6)
vector_value(v)
show(v)
#Output:
#> v = rep(1, 6)
#> vector_reference(v)
#[1] 123 1 1 1 1 1
#> show(v)
#[1] 123 1 1 1 1 1
#> v = rep(1, 6)
#> vector_value(v)
#[1] 123 1 1 1 1 1
#> show(v)
#[1] 1 1 1 1 1 1
*/
Best,
Matt
> Thanks again for your help,
>
> Pierre
>
> Le 26/02/2015 16:30, Jeffrey Pollock a écrit :
>> Perhaps use the clone() function?
>>
>> library(Rcpp)
>>
>> cppFunction("
>> NumericVector par_CMAtR(NumericVector vec_CMA) {
>> NumericVector out = clone(vec_CMA);
>> out[5] = exp(out[5]);
>> return out;
>> }
>> ")
>>
>> vec_C <- rep(1, 6)
>> par_CMAtR(vec_C)
>> print(vec_C)
>>
>> On Thu, Feb 26, 2015 at 3:16 PM, Pierre GLOAGUEN
>> <Pierre.Gloaguen at ifremer.fr <mailto:Pierre.Gloaguen at ifremer.fr>> wrote:
>>
>>
>> Hello everybody,
>>
>> I have a very simple example
>> I have a vector vec_CMA which length is a multiple of 6.
>> I want to get the exact same vector, except the last element
>> which is the exponential of the last element of vec_CMA
>> The code is the following
>>
>> //myfun.cpp
>> #include <Rcpp.h>
>> using namespace Rcpp;
>>
>> // [[Rcpp::export]]
>> NumericVector par_CMAtR(NumericVector vec_CMA){
>> int K = (vec_CMA.size())/6;
>> NumericVector out(6*K);
>> out = vec_CMA;
>> out[6*K-1] = exp(vec_CMA[6*K-1]);
>> return out;
>> }
>>
>> I apply the function with the R code
>> sourceCpp("myfun.cpp")
>> vec_C <- rep(1,6)
>> par_CMAtR(vec_C)
>> [1] 1 1 1 1 1 2.718282
>>
>> 8
>>
>> works fine. Except the vec_C is modified too!
>> vec_C
>> [1] 1 1 1 1 1 2.718282
>>
>> It's the first time I have this kind of problem. What is wrong in
>> my code?
>> Thanks for your help,
>>
>> Pierre Gloaguen
>>
>>
>> _______________________________________________
>> Rcpp-devel mailing list
>> Rcpp-devel at lists.r-forge.r-project.org
>> <mailto:Rcpp-devel at lists.r-forge.r-project.org>
>> https://lists.r-forge.r-project.org/cgi-bin/mailman/listinfo/rcpp-devel
>>
>>
>
>
> _______________________________________________
> Rcpp-devel mailing list
> Rcpp-devel at lists.r-forge.r-project.org
> https://lists.r-forge.r-project.org/cgi-bin/mailman/listinfo/rcpp-devel
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.r-forge.r-project.org/pipermail/rcpp-devel/attachments/20150226/817d6af0/attachment.html>
More information about the Rcpp-devel
mailing list