Skip to content

Enable lambdas in all sugar functions #1373

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 7 commits into from
Mar 31, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
18 changes: 18 additions & 0 deletions ChangeLog
Original file line number Diff line number Diff line change
@@ -1,3 +1,21 @@
2025-03-31 Dirk Eddelbuettel <[email protected]>

* DESCRIPTION (Version, Date): Roll micro version and date
* inst/include/Rcpp/config.h: Idem

2025-03-29 Iñaki Ucar <[email protected]>

* inst/include/Rcpp/traits/result_of.h: Reimplement traits::result_of using
std::result_of (up to C++14) or std::invoke_result (C++17 or later), which
supports previous use cases and enables lambdas
* inst/include/Rcpp/sugar/functions/sapply.h: Use new result_of interface
* inst/include/Rcpp/sugar/functions/lapply.h: Idem
* inst/include/Rcpp/sugar/functions/mapply/mapply_2.h: Idem
* inst/include/Rcpp/sugar/functions/mapply/mapply_3.h: Idem
* inst/include/Rcpp/sugar/matrix/outer.h: Idem
* inst/tinytest/cpp/sugar.cpp: New tests for previous sugar functions
* inst/tinytest/test_sugar.R: Idem

2025-03-26 Dirk Eddelbuettel <[email protected]>

* DESCRIPTION (Version, Date): Roll micro version and date
Expand Down
4 changes: 2 additions & 2 deletions DESCRIPTION
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
Package: Rcpp
Title: Seamless R and C++ Integration
Version: 1.0.14.11
Date: 2025-03-26
Version: 1.0.14.12
Date: 2025-03-31
Authors@R: c(person("Dirk", "Eddelbuettel", role = c("aut", "cre"), email = "[email protected]",
comment = c(ORCID = "0000-0001-6419-907X")),
person("Romain", "Francois", role = "aut",
Expand Down
4 changes: 2 additions & 2 deletions inst/include/Rcpp/config.h
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@
#define RCPP_VERSION_STRING "1.0.14"

// the current source snapshot (using four components, if a fifth is used in DESCRIPTION we ignore it)
#define RCPP_DEV_VERSION RcppDevVersion(1,0,14,11)
#define RCPP_DEV_VERSION_STRING "1.0.14.11"
#define RCPP_DEV_VERSION RcppDevVersion(1,0,14,12)
#define RCPP_DEV_VERSION_STRING "1.0.14.12"

#endif
5 changes: 3 additions & 2 deletions inst/include/Rcpp/sugar/functions/lapply.h
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,8 @@
//
// lapply.h: Rcpp R/C++ interface class library -- lapply
//
// Copyright (C) 2010 - 2011 Dirk Eddelbuettel and Romain Francois
// Copyright (C) 2010 - 2024 Dirk Eddelbuettel and Romain Francois
// Copyright (C) 2025 Dirk Eddelbuettel, Romain Francois and Iñaki Ucar
//
// This file is part of Rcpp.
//
Expand Down Expand Up @@ -33,7 +34,7 @@ class Lapply : public VectorBase<
> {
public:
typedef Rcpp::VectorBase<RTYPE,NA,T> VEC ;
typedef typename ::Rcpp::traits::result_of<Function>::type result_type ;
typedef typename ::Rcpp::traits::result_of<Function, T>::type result_type ;

Lapply( const VEC& vec_, Function fun_ ) :
vec(vec_), fun(fun_){}
Expand Down
15 changes: 8 additions & 7 deletions inst/include/Rcpp/sugar/functions/mapply/mapply_2.h
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,8 @@
//
// mapply_2.h: Rcpp R/C++ interface class library -- mapply_2
//
// Copyright (C) 2012 Dirk Eddelbuettel and Romain Francois
// Copyright (C) 2012 - 2024 Dirk Eddelbuettel and Romain Francois
// Copyright (C) 2025 Dirk Eddelbuettel, Romain Francois and Iñaki Ucar
//
// This file is part of Rcpp.
//
Expand Down Expand Up @@ -32,13 +33,13 @@ template <int RTYPE,
>
class Mapply_2 : public VectorBase<
Rcpp::traits::r_sexptype_traits<
typename ::Rcpp::traits::result_of<Function>::type
typename ::Rcpp::traits::result_of<Function, T_1, T_2>::type
>::rtype ,
true ,
Mapply_2<RTYPE,NA_1,T_1,NA_2,T_2,Function>
> {
public:
typedef typename ::Rcpp::traits::result_of<Function>::type result_type ;
typedef typename ::Rcpp::traits::result_of<Function, T_1, T_2>::type result_type ;

Mapply_2( const T_1& vec_1_, const T_2& vec_2_, Function fun_ ) :
vec_1(vec_1_), vec_2(vec_2_), fun(fun_){}
Expand All @@ -62,14 +63,14 @@ template <int RTYPE,
class Mapply_2_Vector_Primitive : public
VectorBase<
Rcpp::traits::r_sexptype_traits<
typename ::Rcpp::traits::result_of<Function>::type
typename ::Rcpp::traits::result_of<Function, T_1>::type
>::rtype ,
true ,
Mapply_2_Vector_Primitive<RTYPE,NA_1,T_1,PRIM_2,Function>
>
{
public:
typedef typename ::Rcpp::traits::result_of<Function>::type result_type ;
typedef typename ::Rcpp::traits::result_of<Function, T_1>::type result_type ;

Mapply_2_Vector_Primitive( const T_1& vec_1_, PRIM_2 prim_2_, Function fun_ ) :
vec_1(vec_1_), prim_2(prim_2_), fun(fun_){}
Expand All @@ -93,14 +94,14 @@ template <int RTYPE,
class Mapply_2_Primitive_Vector : public
VectorBase<
Rcpp::traits::r_sexptype_traits<
typename ::Rcpp::traits::result_of<Function>::type
typename ::Rcpp::traits::result_of<Function, T_2>::type
>::rtype ,
true ,
Mapply_2_Primitive_Vector<RTYPE,PRIM_1,NA_2,T_2,Function>
>
{
public:
typedef typename ::Rcpp::traits::result_of<Function>::type result_type ;
typedef typename ::Rcpp::traits::result_of<Function, T_2>::type result_type ;

Mapply_2_Primitive_Vector( PRIM_1 prim_1_, const T_2& vec_2_, Function fun_ ) :
prim_1(prim_1_), vec_2(vec_2_), fun(fun_){}
Expand Down
7 changes: 4 additions & 3 deletions inst/include/Rcpp/sugar/functions/mapply/mapply_3.h
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,8 @@
//
// mapply_3.h: Rcpp R/C++ interface class library -- mapply_3
//
// Copyright (C) 2012 Dirk Eddelbuettel and Romain Francois
// Copyright (C) 2012 - 2024 Dirk Eddelbuettel and Romain Francois
// Copyright (C) 2025 Dirk Eddelbuettel, Romain Francois and Iñaki Ucar
//
// This file is part of Rcpp.
//
Expand Down Expand Up @@ -33,13 +34,13 @@ template <
>
class Mapply_3 : public VectorBase<
Rcpp::traits::r_sexptype_traits<
typename ::Rcpp::traits::result_of<Function>::type
typename ::Rcpp::traits::result_of<Function, T_1, T_2, T_3>::type
>::rtype ,
true ,
Mapply_3<RTYPE_1,NA_1,T_1,RTYPE_2,NA_2,T_2,RTYPE_3,NA_3,T_3,Function>
> {
public:
typedef typename ::Rcpp::traits::result_of<Function>::type result_type ;
typedef typename ::Rcpp::traits::result_of<Function, T_1, T_2, T_3>::type result_type ;

typedef Rcpp::VectorBase<RTYPE_1,NA_1,T_1> VEC_1 ;
typedef Rcpp::VectorBase<RTYPE_2,NA_2,T_2> VEC_2 ;
Expand Down
42 changes: 10 additions & 32 deletions inst/include/Rcpp/sugar/functions/sapply.h
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@

// sapply.h: Rcpp R/C++ interface class library -- sapply
//
// Copyright (C) 2010 - 2023 Dirk Eddelbuettel and Romain Francois
// Copyright (C) 2010 - 2024 Dirk Eddelbuettel and Romain Francois
// Copyright (C) 2025 Dirk Eddelbuettel, Romain Francois and Iñaki Ucar
//
// This file is part of Rcpp.
//
Expand All @@ -21,42 +22,19 @@
#ifndef Rcpp__sugar__sapply_h
#define Rcpp__sugar__sapply_h

// This used to be conditional on a define and test in compiler.h
#include <type_traits> // ::std::result_of

namespace Rcpp{
namespace sugar{

template <typename Function, typename SugarExpression>
struct sapply_application_result_of
{
#if __cplusplus >= 201103L
#if __cplusplus < 201703L
// deprecated by C++17, removed by C++2020, see https://en.cppreference.com/w/cpp/types/result_of
typedef typename ::std::result_of<Function(typename SugarExpression::stored_type)>::type type;
#else
// since C++17, see https://en.cppreference.com/w/cpp/types/result_of
typedef typename ::std::invoke_result<Function, typename SugarExpression::stored_type>::type type;
#endif
#else
// TODO this else branch can likely go
typedef typename ::Rcpp::traits::result_of<Function>::type type;
#endif
};

// template <typename Function, typename SugarExpression>
// using sapply_application_result_of_t = typename sapply_application_result_of<Function, SugarExpression>::type;

template <int RTYPE, bool NA, typename T, typename Function, bool NO_CONVERSION>
class Sapply : public VectorBase<
Rcpp::traits::r_sexptype_traits<
typename ::Rcpp::sugar::sapply_application_result_of<Function, T>::type
typename ::Rcpp::traits::result_of<Function, T>::type
>::rtype ,
true ,
Sapply<RTYPE,NA,T,Function,NO_CONVERSION>
> {
public:
typedef typename ::Rcpp::sugar::sapply_application_result_of<Function, T>::type result_type ;
typedef typename ::Rcpp::traits::result_of<Function, T>::type result_type ;
const static int RESULT_R_TYPE =
Rcpp::traits::r_sexptype_traits<result_type>::rtype ;

Expand Down Expand Up @@ -87,13 +65,13 @@ class Sapply : public VectorBase<
template <int RTYPE, bool NA, typename T, typename Function>
class Sapply<RTYPE,NA,T,Function,true> : public VectorBase<
Rcpp::traits::r_sexptype_traits<
typename ::Rcpp::sugar::sapply_application_result_of<Function, T>::type
typename ::Rcpp::traits::result_of<Function, T>::type
>::rtype ,
true ,
Sapply<RTYPE,NA,T,Function,true>
> {
public:
typedef typename ::Rcpp::sugar::sapply_application_result_of<Function, T>::type result_type ;
typedef typename ::Rcpp::traits::result_of<Function, T>::type result_type ;
const static int RESULT_R_TYPE =
Rcpp::traits::r_sexptype_traits<result_type>::rtype ;

Expand Down Expand Up @@ -124,15 +102,15 @@ template <int RTYPE, bool NA, typename T, typename Function >
inline sugar::Sapply<
RTYPE,NA,T,Function,
traits::same_type<
typename ::Rcpp::sugar::sapply_application_result_of<Function, T>::type ,
typename Rcpp::traits::storage_type< traits::r_sexptype_traits< typename ::Rcpp::sugar::sapply_application_result_of<Function, T>::type >::rtype >::type
typename ::Rcpp::traits::result_of<Function, T>::type ,
typename Rcpp::traits::storage_type< traits::r_sexptype_traits< typename ::Rcpp::traits::result_of<Function, T>::type >::rtype >::type
>::value
>
sapply( const Rcpp::VectorBase<RTYPE,NA,T>& t, Function fun ){
return sugar::Sapply<RTYPE,NA,T,Function,
traits::same_type<
typename ::Rcpp::sugar::sapply_application_result_of<Function, T>::type ,
typename Rcpp::traits::storage_type< traits::r_sexptype_traits< typename ::Rcpp::sugar::sapply_application_result_of<Function, T>::type >::rtype >::type
typename ::Rcpp::traits::result_of<Function, T>::type ,
typename Rcpp::traits::storage_type< traits::r_sexptype_traits< typename ::Rcpp::traits::result_of<Function, T>::type >::rtype >::type
>::value >( t, fun ) ;
}

Expand Down
7 changes: 4 additions & 3 deletions inst/include/Rcpp/sugar/matrix/outer.h
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,8 @@
//
// outer.h: Rcpp R/C++ interface class library -- outer
//
// Copyright (C) 2010 - 2011 Dirk Eddelbuettel and Romain Francois
// Copyright (C) 2010 - 2024 Dirk Eddelbuettel and Romain Francois
// Copyright (C) 2025 Dirk Eddelbuettel, Romain Francois and Iñaki Ucar
//
// This file is part of Rcpp.
//
Expand Down Expand Up @@ -31,13 +32,13 @@ template <int RTYPE,
typename Function >
class Outer : public MatrixBase<
Rcpp::traits::r_sexptype_traits<
typename ::Rcpp::traits::result_of<Function>::type
typename ::Rcpp::traits::result_of<Function, LHS_T, RHS_T>::type
>::rtype ,
true ,
Outer<RTYPE,LHS_NA,LHS_T,RHS_NA,RHS_T,Function>
> {
public:
typedef typename ::Rcpp::traits::result_of<Function>::type result_type ;
typedef typename ::Rcpp::traits::result_of<Function, LHS_T, RHS_T>::type result_type ;
const static int RESULT_R_TYPE =
Rcpp::traits::r_sexptype_traits<result_type>::rtype ;

Expand Down
29 changes: 13 additions & 16 deletions inst/include/Rcpp/traits/result_of.h
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,8 @@
//
// result_of.h: Rcpp R/C++ interface class library -- traits to help wrap
//
// Copyright (C) 2010 - 2012 Dirk Eddelbuettel and Romain Francois
// Copyright (C) 2010 - 2024 Dirk Eddelbuettel and Romain Francois
// Copyright (C) 2025 Dirk Eddelbuettel, Romain Francois and Iñaki Ucar
//
// This file is part of Rcpp.
//
Expand All @@ -26,24 +27,20 @@
namespace Rcpp{
namespace traits{

template <typename T>
template <typename T, typename... Args>
struct result_of{
typedef typename T::result_type type ;
} ;

template <typename RESULT_TYPE, typename INPUT_TYPE>
struct result_of< RESULT_TYPE (*)(INPUT_TYPE) >{
typedef RESULT_TYPE type ;
} ;

template <typename RESULT_TYPE, typename U1, typename U2>
struct result_of< RESULT_TYPE (*)(U1, U2) >{
typedef RESULT_TYPE type ;
#if __cplusplus < 201703L
// deprecated by C++17, removed by C++2020, see https://en.cppreference.com/w/cpp/types/result_of
typedef typename ::std::result_of<T(typename Args::stored_type...)>::type type;
#else
// since C++17, see https://en.cppreference.com/w/cpp/types/result_of
typedef typename ::std::invoke_result<T, typename Args::stored_type...>::type type;
#endif
} ;

template <typename RESULT_TYPE, typename U1, typename U2, typename U3>
struct result_of< RESULT_TYPE (*)(U1, U2, U3) >{
typedef RESULT_TYPE type ;
template <typename T>
struct result_of<T>{
typedef typename T::result_type type ;
} ;

}
Expand Down
Loading