Skip to main content
edited tags
Link
Jamal
  • 35.2k
  • 13
  • 134
  • 238
Source Link
glampert
  • 17.3k
  • 4
  • 31
  • 89

writeln() and format() with variadic templates

I wanted to get better acquainted with variadic templates, so I decide to try to implement a function like D's writeln(), just for fun.

void writeln()
{
    std::cout << "\n";
}

template<typename T, typename ...Args>
void writeln(T firstArg, Args... extraArgs)
{
    std::cout << firstArg;
    writeln(std::forward<Args>(extraArgs)...);
}

Usage example:

writeln("hello ", "world ", 42, "\t", 3.141592);
writeln(); // prints just a newline

Next, I implemented a format() function, which writes to a string instead of cout:

// Need this because there is no to_string for string in the std namespace.
std::string to_string(const std::string & s)
{
    return s;
}

std::string format()
{
    return "";
}

template<typename T, typename ...Args>
std::string format(T firstArg, Args... extraArgs)
{
    using namespace std;
    std::string s = to_string(firstArg);
    s += format(std::forward<Args>(extraArgs)...);
    return s;
}

// sample:
std::string s = format("hello ", "world ", 42, "\t", 3.141592);

It is uses std::to_string() for the native types. If I want to print custom types, then I can define a local to_string() and the overload resolution should find it.

My concerns are:

  1. I haven't had many chances to use variadic templates so far, so I might be missing some caveat here. I was expecting it to be more complicated... Did I miss some corner case?

  2. Is my use of std::forward appropriate?

  3. Any other comments and suggestion are very welcome.