1

I recently started programming in c++ and I've bumped into a small problem. If I want my output to be structured (let's say that every line starts with a name and then a number) in a way that the names are written normally to the screen (every first letter of every name starts at the beginning of each new line) and I want the numbers that follow to be lined up in a column, how would I do this? I want the programs output to look like this:

Gary         0
LongName     0
VerylongName 0

I want my program to print something in the way above, but with different lengths of names (and the '0' in this case, lined up in a column).

Martin York
  • 257,169
  • 86
  • 333
  • 562
  • How would you do this? Well, every time you output a line, you write a name and then a number and make sure that number is lined up in a column. How else would you? – R. Martinho Fernandes Oct 28 '13 at 15:30
  • 1
    Put 4 whitespaces before each line in your output section to get cleaner formatting, it's a little unclear what you're asking. – Sam Cristall Oct 28 '13 at 15:30
  • Put it into a table ("The website for some reason won't let me write several whitespaces in a way that can be seen") –  Oct 28 '13 at 15:33
  • Jump in our shoes - read your post and try to figure out what you are asking for. What website ...? – Artur Oct 28 '13 at 15:38

4 Answers4

4

Try the following: if you know the maximum length of all the names you intend to print (e.g. 20), then use the C++ i/o manipulators to set the width of the output (and left-justification). This will force the output to take up max characters.

Code snippet:

#include <iostream>
#include <iomanip>
...
// for each entry
  std::cout << std::setw(20) << std::left << "Gary" << 10 << "\n";
...
std::cout << std::flush;

Here's some more information...

Tom
  • 2,369
  • 13
  • 21
1

I'm shooting in the dark here since you haven't really included much information... HOWEVER one way you can do this is to make sure that you create the columns with padding around the name - and not worry about the numbers. Formatted output is one case where C has an advantage over C++ (IMHO). In C++ you can also do this with something like this:

cout << setw(15) << name << number << "\n";

Bonus points if you figure out ahead of time the maximum length of the name you have and add, say, 4 to it.

Martin York
  • 257,169
  • 86
  • 333
  • 562
Dan L
  • 325
  • 1
  • 6
  • Why do you think C is better. There you would have to find the max length. Use that to build a format string then use the format string to do the printing. Seems like an extra layer of indirection to build a string with a number you have. – Martin York Oct 28 '13 at 15:41
  • Well, I think that doing something like printf("%-15s%3d",name,number) is pretty easy to deal with, and would definitely handle anything the OP asked for... – Dan L Nov 04 '13 at 17:52
  • I can agree that formatted output operators are much more compact in C. But remembering all the detail for those operators is just as hard in either language. The disadvantage of C++ is it is **much** more verbose. But the payoff is type safety (which in the long run is much more important). In C input/output is a source of a lot of bugs (that crash). In C++ that is not going to happen (the compiler tells you when the types don't align). But even in C++ (with boost) you can use the old arcane output format specifiers made popular with C: see http://stackoverflow.com/a/119194/14065 – Martin York Nov 04 '13 at 18:05
  • But going back to the actual thing: `printf("%-15s%3d",name,number)` is not enough. You actually need to build the format string based on the largest name to make sure they align correctly: `sprintf(format,"%%-%ds%%3d",size);printf(format, name, number);` Now that seems a lot harder to read than `cout << left() << setw(size) << name << setw(3) << number << "\n";` – Martin York Nov 04 '13 at 18:10
  • If you don't know how long your names will be and are concerned that you need to address that dynamically, sure, but if you can just toss a value of 20 or something that's a lot easier to deal with. In C you can align the text to the left and the numbers to the right with minimal fuss. Either way though, as I mentioned above, this is IMHO. It's an opinion, you asked me why I thought that way, and I explained. You can continue to love C++ for the set* output formatters, where I will continue to think it's generally messy for every day use. There's nothing wrong with a difference of Opinion:). – Dan L Nov 04 '13 at 22:21
1

Not in the C++ standard library, but still worth mentioning: boost::format. It will let you write printf-like format strings while still being type-safe.

Example:

#include <boost/format.hpp>
#include <iostream>
#include <string>

struct PersonData
{
    std::string name;
    int         age;
};

PersonData persons[] =
{
    {"Gary", 1},
    {"Whitney", 12},
    {"Josephine ", 101}
};

int main(void)
{
    for (auto person : persons)
    {
        std::cout << boost::format("%-20s %5i") % person.name % person.age << std::endl;
    }

    return 0;
}  

Outputs:

Gary                     1
Whitney                 12
Josephine              101
anorm
  • 2,255
  • 1
  • 19
  • 38
0
struct X
{
    const char *s;
    int num;
} tab[] = {
            {"Gary",1},
            {"LongName",23},
            {"VeryLongName",456}
          };

int main(void)
{
    for (int i = 0; i < sizeof(tab) / sizeof(struct X); i++ )
    {
        // C like - example width 20chars
        //printf( "%-20s %5i\n", tab[i].s, tab[i].num );
        // C++ like
        std::cout << std::setw(20) << std::left << tab[i].s << std::setw(5) << std::right << tab[i].num << std::endl;
    }

    getchar();
    return 0;
}  
Artur
  • 7,038
  • 2
  • 25
  • 39