Rcpp Version 0.10.3
 All Classes Namespaces Files Functions Variables Typedefs Enumerator Friends Macros
as.h
Go to the documentation of this file.
1 // -*- mode: C++; c-indent-level: 4; c-basic-offset: 4; indent-tabs-mode: nil; -*-
2 //
3 // as.h: Rcpp R/C++ interface class library -- convert SEXP to C++ objects
4 //
5 // Copyright (C) 2009 - 2013 Dirk Eddelbuettel and Romain Francois
6 // Copyright (C) 2013 Rice University
7 //
8 // This file is part of Rcpp.
9 //
10 // Rcpp is free software: you can redistribute it and/or modify it
11 // under the terms of the GNU General Public License as published by
12 // the Free Software Foundation, either version 2 of the License, or
13 // (at your option) any later version.
14 //
15 // Rcpp is distributed in the hope that it will be useful, but
16 // WITHOUT ANY WARRANTY; without even the implied warranty of
17 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 // GNU General Public License for more details.
19 //
20 // You should have received a copy of the GNU General Public License
21 // along with Rcpp. If not, see <http://www.gnu.org/licenses/>.
22 
23 #ifndef Rcpp__as__h
24 #define Rcpp__as__h
25 
26 #include <Rcpp/internal/Exporter.h>
27 
28 namespace Rcpp{
29 
30  namespace internal{
31 
32  template <typename T> T primitive_as( SEXP x ){
33  if( ::Rf_length(x) != 1 ) throw ::Rcpp::not_compatible( "expecting a single value" ) ;
35  SEXP y = PROTECT( r_cast<RTYPE>(x) );
36  typedef typename ::Rcpp::traits::storage_type<RTYPE>::type STORAGE;
37  T res = caster<STORAGE,T>( *r_vector_start<RTYPE>( y ) ) ;
38  UNPROTECT(1) ;
39  return res ;
40  }
41 
42  template <typename T> T as( SEXP x, ::Rcpp::traits::r_type_primitive_tag ) {
43  return primitive_as<T>(x) ;
44  }
45 
46  inline const char* check_single_string( SEXP x){
47  if( TYPEOF(x) == CHARSXP ) return CHAR( x ) ;
48  if( ! ::Rf_isString(x) )
49  throw ::Rcpp::not_compatible( "expecting a string" ) ;
50  if (Rf_length(x) != 1)
51  throw ::Rcpp::not_compatible( "expecting a single value");
52  return CHAR( STRING_ELT( ::Rcpp::r_cast<STRSXP>(x) ,0 ) ) ;
53  }
54 
55 
56  template <typename T> T as_string( SEXP x, Rcpp::traits::true_type){
57  const char* y = check_single_string(x) ;
58  return std::wstring( y, y+strlen(y)) ;
59  }
60 
61  template <typename T> T as_string( SEXP x, Rcpp::traits::false_type){
62  return check_single_string(x) ;
63  }
64 
65  template <typename T> T as(SEXP x, ::Rcpp::traits::r_type_string_tag ) {
66  return as_string<T>( x, typename Rcpp::traits::is_wide_string<T>::type() );
67  }
68 
69  template <typename T> T as(SEXP x, ::Rcpp::traits::r_type_RcppString_tag ) {
70  if( ! ::Rf_isString(x) ){
71  throw ::Rcpp::not_compatible( "expecting a string" ) ;
72  }
73  if (Rf_length(x) != 1) {
74  throw ::Rcpp::not_compatible( "expecting a single value");
75  }
76  return STRING_ELT( ::Rcpp::r_cast<STRSXP>(x) ,0 ) ;
77  }
78 
79  template <typename T> T as(SEXP x, ::Rcpp::traits::r_type_generic_tag ) {
80  RCPP_DEBUG_1( "as(SEXP = <%p>, r_type_generic_tag )", x ) ;
81  ::Rcpp::traits::Exporter<T> exporter(x);
82  RCPP_DEBUG_1( "exporter type = %s", DEMANGLE(exporter) ) ;
83  return exporter.get() ;
84  }
85 
86  void* as_module_object_internal(SEXP) ;
87  template <typename T> object<T> as_module_object(SEXP x){
88  return (T*) as_module_object_internal(x) ;
89  }
90 
92  template <typename T> T as(SEXP x, ::Rcpp::traits::r_type_module_object_pointer_tag ) {
93  return as_module_object<typename T::object_type>( x ) ;
94  }
95 
97  template <typename T> T as(SEXP x, ::Rcpp::traits::r_type_module_object_tag ){
98  T* obj = as_module_object<T>(x) ;
99  return *obj ;
100  }
101 
103  template <typename T> T as(SEXP x, ::Rcpp::traits::r_type_enum_tag ){
104  return T( primitive_as<int>(x) ) ;
105  }
106 
107  }
108 
109 
125  template <typename T> T as( SEXP m_sexp) {
126  return internal::as<T>( m_sexp, typename traits::r_type_traits<T>::r_category() ) ;
127  }
128 
129  template <typename T>
130  inline typename traits::remove_const_and_reference<T>::type bare_as( SEXP m_sexp ){
131  return as< typename traits::remove_const_and_reference<T>::type >( m_sexp ) ;
132  }
133 
134  template<> inline SEXP as(SEXP m_sexp) { return m_sexp ; }
135 
136 } // Rcpp
137 
138 #endif