[Rcpp-devel] ivec and imat don't pass by reference
Dirk Eddelbuettel
edd at debian.org
Tue Sep 15 13:53:32 CEST 2015
On 15 September 2015 at 12:16, Serguei Sokol wrote:
| Hi,
|
| If we declare the following toy function where a numeric matrix is passed by reference,
| it works as expected, the matrix m is modified "in place":
|
| cppFunction('
| mat m2(mat& m) {
| m=m*2;
| return(m);
| }', depends="RcppArmadillo", inc="using namespace arma;")
| m=matrix(1:4, 2)+pi
| m2(m)
| [,1] [,2]
| [1,] 8.283185 12.28319
| [2,] 10.283185 14.28319
| m
| [,1] [,2]
| [1,] 8.283185 12.28319
| [2,] 10.283185 14.28319
|
| But if we pass to imat type, the call by reference is no more functionning:
| cppFunction('
| imat im2(imat& m) {
| m=m*2;
| return(m);
| }', depends="RcppArmadillo", inc="using namespace arma;")
| im=matrix(1:4, 2)
| im2(im)
| [,1] [,2]
| [1,] 2 6
| [2,] 4 8
| im
| [,1] [,2]
| [1,] 1 3
| [2,] 2 4
|
| The original matrix im remains as it was.
| You can easyly verify that the same is true for ivec type.
| Is it intended behaviour?
It is something else, which is a slight trick: your 'm' is not an integer
matrix, so you are forcing a copy, which breaks the reference semantics.
See here using your code:
R> library(Rcpp)
R> cppFunction('imat im2(imat& m) { m=m*2; return(m); }', depends="RcppArmadillo", inc="using namespace arma;")
R> m <- matrix(c(1L,2L,3L,4L), 2)
R> m
[,1] [,2]
[1,] 1 3
[2,] 2 4
R> storage.mode(m)
[1] "integer"
R> im2(m)
[,1] [,2]
[1,] 2 6
[2,] 4 8
R> m
[,1] [,2]
[1,] 2 6
[2,] 4 8
R>
So if we pass an integer matrix down, it gets changed as a side effect.
Dirk
--
http://dirk.eddelbuettel.com | @eddelbuettel | edd at debian.org
More information about the Rcpp-devel
mailing list