[Rcpp-commits] r1662 - pkg/Rcpp/inst/doc/Rcpp-sugar
noreply at r-forge.r-project.org
noreply at r-forge.r-project.org
Wed Jun 23 12:04:55 CEST 2010
Author: romain
Date: 2010-06-23 12:04:55 +0200 (Wed, 23 Jun 2010)
New Revision: 1662
Modified:
pkg/Rcpp/inst/doc/Rcpp-sugar/Rcpp-sugar.Rnw
Log:
some more content in the sugar vignette
Modified: pkg/Rcpp/inst/doc/Rcpp-sugar/Rcpp-sugar.Rnw
===================================================================
--- pkg/Rcpp/inst/doc/Rcpp-sugar/Rcpp-sugar.Rnw 2010-06-23 09:28:11 UTC (rev 1661)
+++ pkg/Rcpp/inst/doc/Rcpp-sugar/Rcpp-sugar.Rnw 2010-06-23 10:04:55 UTC (rev 1662)
@@ -399,6 +399,13 @@
\section{Implementation}
+This section details some of the techniques used in the implementation
+of \sugar. Note that the user need not to be familiar with the implementation
+details in order to use \sugar.
+
+Writing \sugar~functions is very mechanical and somewhat easy when the
+basic concepts are mastered (which might take time).
+
\subsection{The curiously recurring template pattern}
Expression templates such as those used by \sugar~use a technique
@@ -480,28 +487,28 @@
<<lang=cpp>>=
template <int RTYPE, bool NA, typename T, typename Function>
class Sapply : public VectorBase<
- Rcpp::traits::r_sexptype_traits<
- typename ::Rcpp::traits::result_of<Function>::type
- >::rtype ,
- true ,
- Sapply<RTYPE,NA,T,Function>
+ Rcpp::traits::r_sexptype_traits<
+ typename ::Rcpp::traits::result_of<Function>::type
+ >::rtype ,
+ true ,
+ Sapply<RTYPE,NA,T,Function>
> {
public:
- typedef typename ::Rcpp::traits::result_of<Function>::type ;
- const static int RESULT_R_TYPE =
- Rcpp::traits::r_sexptype_traits<result_type>::rtype ;
-
- typedef Rcpp::VectorBase<RTYPE,NA,T> VEC ;
- typedef typename Rcpp::traits::r_vector_element_converter<RESULT_R_TYPE>::type converter_type ;
- typedef typename Rcpp::traits::storage_type<RESULT_R_TYPE>::type STORAGE ;
-
- Sapply( const VEC& vec_, Function fun_ ) : vec(vec_), fun(fun_){}
-
- inline STORAGE operator[]( int i ) const {
- return converter_type::get( fun( vec[i] ) );
- }
- inline int size() const { return vec.size() ; }
-
+ typedef typename ::Rcpp::traits::result_of<Function>::type ;
+ const static int RESULT_R_TYPE =
+ Rcpp::traits::r_sexptype_traits<result_type>::rtype ;
+ typedef Rcpp::VectorBase<RTYPE,NA,T> VEC ;
+ typedef typename Rcpp::traits::r_vector_element_converter<RESULT_R_TYPE>::type
+ converter_type ;
+ typedef typename Rcpp::traits::storage_type<RESULT_R_TYPE>::type STORAGE ;
+
+ Sapply( const VEC& vec_, Function fun_ ) : vec(vec_), fun(fun_){}
+
+ inline STORAGE operator[]( int i ) const {
+ return converter_type::get( fun( vec[i] ) );
+ }
+ inline int size() const { return vec.size() ; }
+
private:
const VEC& vec ;
Function fun ;
@@ -545,12 +552,12 @@
<<lang=cpp>>=
template <typename T>
struct result_of{
- typedef typename T::result_type type ;
+ typedef typename T::result_type type ;
} ;
template <typename RESULT_TYPE, typename INPUT_TYPE>
struct result_of< RESULT_TYPE (*)(INPUT_TYPE) >{
- typedef RESULT_TYPE type ;
+ typedef RESULT_TYPE type ;
} ;
@
@@ -566,11 +573,92 @@
trait is used to identify the expression type.
<<lang=cpp>>=
-const static int RESULT_R_TYPE = Rcpp::traits::r_sexptype_traits<
- typename ::Rcpp::traits::result_of<Function>::type
->::rtype ;
+const static int RESULT_R_TYPE =
+ Rcpp::traits::r_sexptype_traits<result_type>::rtype ;
@
+\subsubsection{Converter}
+
+The \texttt{r\_vector\_element\_converter} class is used to convert an
+object of the function's result type to the actual storage type suitable
+for the sugar expression.
+
+<<lang=cpp>>=
+typedef typename Rcpp::traits::r_vector_element_converter<RESULT_R_TYPE>::type
+ converter_type ;
+
+@
+
+\subsubsection{Storage type}
+
+The \texttt{storage\_type} trait is used to get access to the storage type
+associated with a sugar expression type. For example, the storage type
+of a \texttt{REALSXP} expression is \texttt{double}.
+
+<<lang=cpp>>=
+typedef typename Rcpp::traits::storage_type<RESULT_R_TYPE>::type STORAGE ;
+@
+
+\subsubsection{Input expression base type}
+
+The input expression --- the expression over which \texttt{sapply} runs --- is
+also typedef'ed for convenience:
+
+<<lang=cpp>>=
+typedef Rcpp::VectorBase<RTYPE,NA,T> VEC ;
+@
+
+\subsubsection{Output expression base type}
+
+In order to be part of the \sugar~system, the type generated by the
+\texttt{Sapply} class template must inherit from \texttt{VectorBase}.
+
+<<lang=cpp>>=
+template <int RTYPE, bool NA, typename T, typename Function>
+class Sapply : public VectorBase<
+ Rcpp::traits::r_sexptype_traits<
+ typename ::Rcpp::traits::result_of<Function>::type
+ >::rtype ,
+ true ,
+ Sapply<RTYPE,NA,T,Function>
+>
+@
+
+The expression built by \texttt{Sapply} depends on the result type
+of the function, may contain missing values, and the third argument
+is the manifestation of the \emph{CRTP}.
+
+\subsubsection{Constructor}
+
+The constructor of the \texttt{Sapply} class template is straightforward, it
+simply consists of holding the reference to the input expression and the
+function.
+
+<<lang=cpp>>=
+Sapply( const VEC& vec_, Function fun_ ) : vec(vec_), fun(fun_){}
+
+private:
+ const VEC& vec ;
+ Function fun ;
+@
+
+\subsunsection{Implementation}
+
+The indexing operator and the \texttt{size} member function is what
+the \texttt{VectorBase} expects. The size of the result expression is
+the same as the size of the input expression and the i\textsuperscript{th}
+element of the result is simply retrieved by applying the function
+and the converter. Both these methods are inline to maximize performance:
+
+<<lang=cpp>>=
+inline STORAGE operator[]( int i ) const {
+ return converter_type::get( fun( vec[i] ) );
+}
+inline int size() const { return vec.size() ; }
+@
+
+
+
\bibliographystyle{abbrvnat}
\bibliography{Rcpp}
More information about the Rcpp-commits
mailing list