1

I am using RCPP to build a C++ function quicksort for quicksort. I am trying to compile and load this function through the cxxfunction in R. I need to use the cxxFunction. I am getting the following message in R:

error: cannot convert 'Rcpp::IntegerVector {aka Rcpp::Vector<13, Rcpp::PreserveStorage>}' to 'int*' for argument '1' to 'int quicksort(int*, int, int)' make: *** [file15ecb338ec.o] Error 1

Can anyone tell me what is wrong with this?

incl <- 'int quicksort(int xx[], int left, int right) {

int i = left; 
int j = right;
int tmp;
int pivot = xx[(left + right) / 2];

/* partition */
while (i <= j) {
while (xx[i] < pivot)
i++;
while (xx[j] > pivot)
j--;
if (i <= j) {
tmp = xx[i];
xx[i] = xx[j];
xx[j] = tmp;
i++;
j--;
}
}

/* recursion */
if (left < j){
quicksort(xx, left, j);
}
if (i < right){
quicksort(xx, i, right);
}

return (quicksort(xx,i,j));
}
'
sortCpp <- cxxfunction(signature( x = "integer",left = "integer",
                                  right = "integer"),
                       body = 'IntegerVector arr(x);
                       int a = as<int>(left);
                       int b = as<int>(right);
                       return wrap(quicksort(arr,a,b));',
                       include = incl,
                       plugin = "Rcpp",
                       verbose = TRUE)

Just to see if I could call a recursive function using cxxfunction I created a factorial function and called this through cxxfunction and it worked fine.

incl <- 'int factorial(int n)
{
  return (n == 1 || n == 0) ? 1 : factorial(n - 1) * n;
}
'


factcpp <- cxxfunction(signature( x = "integer"),
                       plugin = "Rcpp",
                       include = incl,
                       body = 'int xnew = as<int>(x);
                       return wrap( factorial(x) );
                       ',
                       verbose = TRUE)

1 Answer 1

1

The problem is exactly what the compiler says. Your function expects an int* but you are passing it an Rcpp::IntegerVector. Looking at the documentation for Rcpp::IntegerVector, you can retrieve the raw pointer by .begin(), so you would call via quicksort(arr.begin(), a, b).

Also, unless you really need to roll your own quicksort, I would just use the Standard Library's std::sort:

src <- 'Rcpp::IntegerVector v = Rcpp::IntegerVector(vp);
        std::sort(v.begin(), v.end());
        return wrap(v);'
fun <- cxxfunction(signature(vp="integer"), body=src, plugin="Rcpp")
fun( c(5, 2, 7, -3) )
Sign up to request clarification or add additional context in comments.

7 Comments

I amended the line in the cxxfunction to 'return wrap(quicksort(arr.begin(),a,b));' I am now getting a 'error: 'quicksort' was not declared in this scope' error?
I placed the include before the body parameter in cxxfunction with your amendment and it compiled without errors!. when I ran sortCpp(y) on a vector of integers I got Error in sortCpp(y) : argument "left" is missing, with no default? Do you know what is the problem here?
You are not passing in left and right into sortCpp; and you defined sortCpp to expect those arguments.
When you wrote quicksort, you defined a left and right index for the part of the array to sort. I'm not sure if you defined the range to be inclusive [left, right] or half-open [left, right), but in the former case, to sort the entire array you would want to replace the quicksort(arr.begin(), a, b) with quicksort(arr.begin(), 0, arr.size() - 1) and in the latter case you want quicksort(arr.begin(), 0, arr.size()). Or, if you do intend sortCpp to sort a particular range in the array, you would call sortCpp(someVector, left, right) as you defined.
The expression is ill-formed as you concatenated my two expressions in a way that doesn't make any sense.. I highly recommend you get a better understanding of C++ first or you will run into a lot of frustration. I'm also 100% sure your quicksort doesn't work as it is recursive on all control paths. It will cause an infinite loop/stack overflow.
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.