Интерфейс C ++ и R, получение вывода

Я только начал изучать R, зацикливаясь на тривиальных проблемах. Я пытаюсь выяснить, как значения выводятся в R. В C ++ мы просто используем возвращаемую переменную, но, похоже, это не так с R. Скажем, у меня есть функция, которая принимает 4 входных аргумента, передает эти аргументы в Функция c ++, которая выполняет необходимые вычисления, теперь, если я хочу загрузить этот myfun в R и получить выходные данные из функции c ++, что мне нужно сделать? Ниже приведен шаблон, который я пытаюсь использовать.

extern "C" {
SEXP myfun(SEXP S, SEXP A, SEXP B, SEXP C) { //will call this function from R.
SEXP rate, dir, list, list_names; //declare variables

PROTECT( rate = allocMatrix(REALSXP, 10, 2) ); //allocate 10x2 matrix of double type?
PROTECT( dir = allocVector(INTSXP, 10) ); //allocated vector(10) of int type?

double* p_rate = REAL(rate); //why do I need pointers?
int* p_dir = INTEGER(dir);

// здесь я вызываю функцию C ++, которая вычисляет vector<vector<double> > someVal а также vector<int> someVal2,

Теперь я хочу передать эти значения в скорость и реж.

 for(int i =0; i < 10; i++){
rate[i][0] = someVal1[i][0];
rate[i][1] = someVal1[i][1];
dir[i] = someVal2[i];
}

но компилятору это не нравится. Я не уверен, как использовать указатели p_rate и p_dir в этом случае.

Кроме того, я не совсем понимаю, почему следующий код таков. Кажется, что он передает строки, rate и dir в list_names, а значения в rate и dir. Почему мы не можем просто сделать cout и напечатать нужные значения?

   char *tag[2] = {"rate","dir"};
PROTECT(list_names = allocVector(STRSXP ,2));
SET_STRING_ELT(list_names, 0, mkChar(tag[0]));
SET_STRING_ELT(list_names, 1, mkChar(tag[1]));
PROTECT(list = allocVector(VECSXP ,2));
SET_VECTOR_ELT(list, 0, rate);
SET_VECTOR_ELT(list, 1, dir);
setAttrib(list, R_NamesSymbol , list_names);

UNPROTECT(8);
return (list);
}

Я не понимаю основную идею возврата переменных в R, это кажется очень запутанным. Я был бы очень признателен, если бы кто-то мог указать мне на соответствующие ресурсы, которые объясняют эти вещи.

Заранее спасибо за помощь!

6

Решение

Если вы уже знакомы с C ++, вы можете найти наши Rcpp полезен проект по интеграции R и C ++. Это содержит много документации и примеров, плюс в CRAN теперь используется более 80 пакетов, что дает еще один большой набор примеров.

Вы можете начать с виньетки «Введение», которая соответствует нашей JSS бумага, а также внимательно [rcpp] отметьте здесь

В противном случае вы вернетесь к API R, который более прост и основан только на Си.

9

Другие решения

Как мы уже говорили, отвечая на ваши предыдущий вопрос, дать Rcpp выстрел, и уберите все помехи в вашем коде.

#include <Rcpp.h>
using namespace Rcpp ;

void yourCode( std::vector< std::vector<double> >& someVal,
std::vector<double>& someVal2 ){ ... }

extern "C" SEXP myfun() {
NumericMatrix rate(10, 2);
NumericVector dir(10) ;

std::vector< std::vector<double> > someVal ;
std::vector< double > someVal2 ;

// call whatever function that fills someVal and someVal2
yourCode( someVal, someVal2 ) ;

// fills rate and dir
for(int i =0; i < 10; i++){
rate(i, 0) = someVal1[i][0];
rate(i, 1) = someVal1[i][1];
dir[i] = someVal2[i];
}

// structure the output
List result = List::create(
_["rate"] = rate,
_["dir"] = dir
) ;

return result ;

}
5

По вопросам рекламы [email protected]