Sie müssen ::std::tuple<Args...>
verwenden, um es zu speichern. Aber dann ist die Frage, wie man es auspackt, wenn Sie es brauchen. Dazu müssen Sie eine Technik namens "Indizes" verwenden.
Also, hier ist ein Link zu einem Ort, wo ich ungefähr getan habe, was Sie tun möchten. Die relevanteste Klasse hier, die eine Art Herzstück ist, ist suspended_call
.
https://bitbucket.org/omnifarious/sparkles/src/tip/sparkles/deferred.hpp?at=default
In nur ein bisschen, werde ich die wichtigsten Bits extrahieren und sie in Bezug auf den Code setzen.
This line:
auto saved_args = ::std::make_tuple(::std::move(args)...);
speichert die Argumente in ein Tupel. Ich habe ::std::move
dort verwendet, und ich denke, das ist das Richtige zu tun. Aber es ist möglich, dass ich falsch liege und ich sollte ::std::forward
verwenden. Ich war nie klar über den genauen Unterschied, abgesehen von der Signalabsicht.
Der Code, der den Aufruf mit den gespeicherten Argumenten tatsächlich ausführt, kann here gefunden werden. Jetzt ist dieser Code ziemlich genau, was genau ich mache. Das Bit, das den Indextrick implementiert, beinhaltet das Erstellen eines Satzes von Ganzzahlen, die den Indizes zugeordnet werden, die als Argumente die ::std::get<I>
Vorlage verwenden. Sobald Sie dieses Paket mit ganzen Zahlen haben, können Sie es verwenden, um den Aufruf auf zu erweitern, um alle Tupel-Elemente als einzelne Argumente zu erhalten.
Ich werde versuchen, mit dem Code zu entwickeln, die in einer relativ einfachen Art und Weise funktioniert das:
#include <tuple>
#include <cstddef>
#include <string>
#include <utility>
template < ::std::size_t... Indices>
struct indices {};
template < ::std::size_t N, ::std::size_t... Is>
struct build_indices : build_indices<N-1, N-1, Is...>
{};
template < ::std::size_t... Is>
struct build_indices<0, Is...> : indices<Is...>
{};
template <typename FuncT, typename ArgTuple, ::std::size_t... Indices>
auto call(const FuncT &f, ArgTuple &&args, const indices<Indices...> &)
-> decltype(f(::std::get<Indices>(::std::forward<ArgTuple>(args))...))
{
return ::std::move(f(::std::get<Indices>(::std::forward<ArgTuple>(args))...));
}
template <typename FuncT, typename ArgTuple>
auto call(const FuncT &f, ArgTuple &&args)
-> decltype(call(f, args,
build_indices< ::std::tuple_size<ArgTuple>::value>{}))
{
const build_indices< ::std::tuple_size<ArgTuple>::value> indices;
return ::std::move(call(f, ::std::move(args), indices));
}
int myfunc(::std::string name, const unsigned int foo)
{
return 0;
}
int foo(::std::tuple< ::std::string, const unsigned int> saved_args)
{
return call(myfunc, ::std::move(saved_args));
}
Viele dieser Code entlehnt wurde von this page on the indices trick.
Auch das ist eine Art von Beispiel, das Sie leicht an Ihre spezifische Situation anpassen müssen. Rufen Sie einfach call(nestFunc, saved_args)
irgendwo an.
'std :: tuple' - auch 'std :: bind' und 'std :: function' und all das lustige Zeug. –
Xeo