wonko realtime
wonko realtime

Reputation: 565

Equivalent of %05d with std::stringstream for negative numbers?

I'm trying to create a replacement for sprintfs' %05d behavior. Althought, I've found a similar question here on stackoverflow, the proposed solution there doesn't work for me when I'm testing with negative numbers.

Doing a "sprintf(buf, "%05d", -12)", I'm getting "-0012" back which looks nice.

Using stringstream, width and fill, I'm getting "00-12" which seams reasonable when looking at the docs from std::basic_ios::fill

The fill character is the character used by output insertion functions to fill spaces when padding results to the field width.

but doesn't look like something one could wish.

So I'm confused and don't know if I'm doing something obvious wrong or if width/fill from the std streams doesn't easily support this situation.

A compilable testcode can be found on codepad. Here's an extract of the stream based conversion:

std::string NumberToString(const long iVal, const int iNumDigit)
{
    std::stringstream ss;

    if      (iNumDigit >= 0) ss.fill(' ');
    else if (iNumDigit < 0)  ss.fill('0');
    ss.width(std::abs(iNumDigit));

    ss << iVal;

    return ss.str();
}

EDIT1: Solution:

To match the std stream approach with printf formatting for %05d, jrok's solution can be used for the case with leading zeros. Here's the new function:

std::string NumberToString(const long iVal, const int iNumDigit)
{
    std::stringstream ss;

    if      (iNumDigit >= 0) ss.fill(' ');
    else if (iNumDigit < 0)  { ss.fill('0'); ss.setf(std::ios::internal, std::ios::adjustfield); }
    ss.width(std::abs(iNumDigit));

    ss << iVal;

    return ss.str();
}

Upvotes: 3

Views: 3207

Answers (1)

jrok
jrok

Reputation: 55415

Use stream manipulator std::internal. It (along with std::left and std::right) lets you specify where the fill characters go. For example

std::cout << std::setw(5) << std::setfill('0') << std::internal << -1;

will print -0001.

Upvotes: 6

Related Questions