tipos programacion plantillas plantilla planilla funciones ats c++ templates c++11 function-pointers

c++ - programacion - Pasando cualquier función como parámetro de plantilla



programacion ats funciones (3)

Quiero pasar un valor de función como un parámetro de plantilla a una función. Actualmente lo mejor que pude hacer es:

template< typename F, F f > void pass() { ... }

... que se utiliza:

pass< decltype(&func), &func >();

Lo que realmente me gustaría es tener:

pass< &func >();

¿Hay alguna manera de lograr esto sin macros? ¿Básicamente para pasar tanto el tipo como el valor al mismo tiempo? El compilador obviamente tiene toda la información necesaria para eso ...

La solución debe funcionar con parámetros variables y tipos de retorno. El valor de la función se utiliza en tiempo de compilación, por lo que no se puede pasar como un argumento.

C ++ 11 soluciones bienvenidas.

Edición: caso de uso : estoy generando enlaces en tiempo de compilación, donde necesito crear una función de C ++ para cada función pasada. El caso de uso de este código se ve (simplificado) más o menos así:

template < typename F, F f > int function_wrapper( lua_State* L ) { return dispatcher<typename return_type<F>::type>::call( L, 1, f ); } void register_native_function( lua_Function f, const char* name ) { // binding call using pure C function f } template < typename F, F f > void register_function( const char* name ) { register_native_function( function_wrapper< F, f >, name ); }

Tenga en cuenta que necesito crear una envoltura de función de tiempo de compilación, por lo que necesito el valor de función de paso en tiempo de compilación. Existen soluciones de enlace que permiten el enlace en tiempo de ejecución, pero siempre requieren código repetitivo en comparación con los enlaces escritos a mano. Mi objetivo es lograr un rendimiento escrito a mano aquí.


Ahora es posible en C ++ 17 con la template<auto> :

template<auto Func> struct FuncWrapper final { template<typename... Args> auto operator()(Args &&... args) const { return Func(std::forward<Args>(args)...); } }; int add(int a, int b) { return a + b; } int main() { FuncWrapper<add> wrapper; return wrapper(12, 34); }

Demostración: https://godbolt.org/g/B7W56t

Puede usar #ifdef __cpp_nontype_template_parameter_auto para detectar el soporte del compilador para esto en su código.



Necesitas hacer un typedef para cualquier tipo de función que quieras pasar como un puntero, como esto:

typedef int (*MyFunctionType)(int); template <typename FunctionTypedef, typename ReturnType, typename ParameterType> ReturnType callFunction(FunctionTypedef functionPointer, ParameterType i) { static MyFunctionType myFunctionPointer = functionPointer; return (*functionPointer)(i); } int myFunction(int i) { } int main() { int i = 7; MyFunctionType myFunctionPointer = myFunction; return callFunction<MyFunctionType, int, int>(myFunctionPointer, i); }

Editar: Si desea almacenar estos punteros de función escritos de forma arbitraria, cree una clase base con una función de "función de llamada" virtual y una clase derivada con plantilla que implemente esta función.