简体   繁体   中英

Unpacking Argument List with Variadic Template

I'm trying to create a C++ convenience wrapper around an old C-API that uses an opaque data type. There's one particular C-function which takes a format string, along with a variable number of arguments using the C <stdarg.h> facilities. As part of my wrapper, I want to be able to pass an arbitrary number of arguments (including C++ objects) to this function. However, since obviously the <stdarg.h> facilities can't work with non-POD data, I created a templated conversion function which converts C++ objects (like std::string ) into POD equivalents.

I thought this whole thing would be an easy exercise using C++0x variadic templates, but I'm having difficulty figuring out how to write this function in a way that properly unrolls the argument pack while applying my conversion function to each argument.

What I have so far is:

   template <class T, class... Args>
   void apply(OPAQUE* object, const char* fmt_string, T&& val, Args&&... args)
   {
      apply(object, fmt_string, Convert(val), args...);
   }

   template <class... Args>
   void apply(OPAQUE* object, const char* fmt_string, Args&&... args)
   {
      C_API_Function_Call(object, fmt_string, args...);
   }

Of course, this doesn't work because the recursive function call never actually unpacks the Args... , so it just recurses until the stack overflows. I can't figure out how to make it unpack the arguments while also passing the current argument to the Convert function, and then recursively passing along the result.

Is there anyway to do this?

I think you need the same syntax as when you do perfect forwarding :

template <class... Args>
void apply(OPAQUE* object, const char* fmt_string, Args&&... args)
{
   C_API_Function_Call(object, fmt_string, Convert(std::forward<Arg>(args))...);
}

The ellipsis ... can be placed at the right of an expression containing the argument pack, and not only directly at the right of the argument pack itself.

So, :
func(args...) expand to func(arg1, arg2, arg3, [...] , argN)
func(args)... expand to func(arg1), func(arg2), [...] , func(argN)

At the moment C++0x draft does not provide any solution for that. Because problem is similar to expanding tuples, you can read this discussion and write similar expanding function.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM