c++loopsascii-art

How to print a vertical histogram in C++


#include <iostream>
using namespace std;
int main()
{
    int a, b, c, i;
    cin >> a >> b >>  c;
    
    for ( i = 0;  i < a; i++)
        cout << "*" << endl;
        
    for ( i = 0; i < b; i++)
        cout << "*" << endl;
    
    for ( i = 0; i < c; i++)
        cout << "*" << endl;
}

I'm aware that output is as same as:

for ( i = 0; i < a + b + c; i++ ){
cout << "*" << endl;
}

So for 2 3 1 i get:

What i want is:

     *

*    * 

*    *    *   //Horizontal distance between 2 shapes don't matter.

I've no idea about how to put cursor in the right place considering the printing must be done from up to down.

I hope following example helps and also, if possible, printing of each column must be done by using a separate function.

First loop:

*

*

Second loop:

    *

*   *

*   *

Last loop:

    *

*   *

*   *   *

Printing must be done in exactly that order. Print first column, then second and goes on like this.


Solution

  • You need to rethink your printing a little. To start with you need to find out the highest column, as this is the number of lines you will have.

    I would do something like this:

    int high = std::max(std::max(a, b), c);
    
    for (int i = high; i > 0; i--)
    {
        if (i <= a)
            std::cout << " * ";
        else
            std::cout << "   ";
    
        if (i <= b)
            std::cout << " * ";
        else
            std::cout << "   ";
    
        if (i <= c)
            std::cout << " * ";
        else
            std::cout << "   ";
    
        std::cout << std::endl;
    }
    

    If you want arbitrary number of columns, you might want to put them in a std::vector, and have a inner loop for that.


    For an arbitrary amount of columns, you could use something like:

    // Get the input
    std::cout << "Please enter numbers, all on one line, and end with ENTER: ";
    std::string input;
    std::getline(std::cin, input);
    
    // Parse the input into integers
    std::istringstream istr(input);
    std::vector<int> values(std::istream_iterator<int>(istr),
                            std::istream_iterator<int>());
    
    // Get the max value
    int max_value = *std::max_element(values.begin(), values.end());
    
    // Print the columns
    for (int current = max_value; current > 0; current--)
    {
        for (const int& value : values)
        {
            if (current <= value)
                std::cout << " * ";
            else
                std::cout << "   ";
        }
    
        std::cout << std::endl;
    }