简体   繁体   中英

how to loop over function's arguments without variadic function

Without using variadic function, is it possible to loop over a function's arguments?

This would help me in my question gcc instrumentation - is it possible to automatically output the arguments of a function?

If you just want to output the parameters, a variadic template function could do the trick – offering the type safety a variadic function is lacking...

void print() { }

template <typename T, typename ... TT>
void print(T const& t, T const& ... tt)
{
    std::cout << t << ' ';
    print(tt...);
}

template <typename F, typename ... TT>
void execute(F f, TT&& ... tt)
{
    std::cout << "calling function with arguments: ";
    print(tt...);
    std::cout << std::endl;

    f(std::forward<TT>(tt)...);
}

Even more elegant, if C++17 is available, is a fold expression:

template <typename F, typename ... TT>
void execute(F f, TT&& ... tt)
{
    std::cout << "calling function with arguments: ";
    char const* comma = "";
    ((std::cout << comma << tt, comma = ", "), ...);
    std::cout << std::endl;

    f(std::forward<TT>(tt)...);
}

Note how here modifying the comma variable allows to separate the arguments in the output string by commas without adding a trailing one.

If you allow a bit of pre-compiler magic, we even could include the function name:

template <typename F, typename ... TT>
void execute_(F f, char const* name, TT&& ... tt)
{
    std::cout << "calling function '" << name << "' with arguments: ";
    // ...
}

#define execute(FUNCTION, ...) execute_(FUNCTION, #FUNCTION, ## __VA_ARGS__)
// be aware of GCC extension:                                ^^
// catching empty arguments list!

// alternative variant, not relying on extensions but requiring C++20:
#define execute(F, ...) execute_(F, #F __VA_OPT__(,) __VA_ARGS__)

Usage example here (including a print variant not relying on an empty base function: print2 )...

It has a bit a taste of workaround (sure, you need another function call and 1 lambdas might look ugly), but you get the result with pure C++ means and no ugly tricks – apart from the macro, obviously; given variant relies on a GCC extension.


1 Not any more with the fold expression.

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