Search code examples
c++arraysdictionaryhashmap

Is there a way to display cpp map in a specific way


I need to display the following seats to users and be able to reserve them and cancel the reservation.

class luxaryBus {
    public:
            std::map<std::string, int> seats{ {"1A", 0}, {"1B", 0}, {"1C", 0}, {"1D", 0},{"1E", 0},
                                        {"2A", 0}, {"2B", 0}, {"2C", 0}, {"2D", 0},{"2E", 0},
                                        {"3A", 0}, {"3B", 0}, {"3C", 0}, {"3D", 0},{"3E", 0},
                                        {"4A", 0}, {"44", 0}, {"4C", 0}, {"4D", 0},{"4E", 0},
                                        {"5A", 0}, {"5B", 0}, {"5C", 0}, {"5D", 0},{"5E", 0},
                                        {"6A", 0}, {"6B", 0}, {"6C", 0}, {"6D", 0},{"6E", 0},
                                        {"7A", 0}, {"7B", 0}, {"7C", 0}, {"7D", 0},{"7E", 0},
                                        {"8A", 0}, {"8B", 0}, {"8C", 0}, {"8D", 0},{"8E", 0},
                                        {"9A", 0}, {"9B", 0}, {"9C", 0}, {"9D", 0},{"9E", 0},
                                        {"10 A", 0}, {"10B", 0}, {"10C", 0}, {"10D", 0},{"10E", 0},
                                        {"11 A", 0}, {"11B", 0}};
    
    void displaySeats();
}



void luxaryBus::displaySeats()
{
int test = 0;
    for (const auto& p : this->seats) {
        if (test == 5) {
            std::cout << std::endl;
            test = 0;
        }
        test++;
        std::cout << p.first << p.second << "\t ";
    }
}

Apparently, it is sorting the strings in a way that doesn't work for me:

1A 10A 10B 10C etc...

I tried unordered_map also but no matter what I do I cannot make map display the seats in the way I want (1A, 1B, 1C, 1D, 1E).

1A 1B 1C 1D 1E

2A 2B 2C 2D 2E ....

Tried to change the seat name to A1 B1 C1 D1... Obviously I am new to C++. I know that map is ordered.And I know that using unordered_map there is no way I can guarantee the way the map will be displayed.

My question is, can I use map in a specific way so I can display it in a way that I want to. Or, is there another data structure in c++ that I can use for my task.

Array was my first choice, however, I found it difficult to follow which seat was sold and handle cancellation. Now I can make it work with 2 arrays, one for string representation and one for handling the operations with reservation and cancellation.

Can anyone give me a suggestion how to tackle this problem ?


Solution

  • std::map uses comparison operator< to compare keys in the map. However, the problem is that strings are being compared lexicographically, so both "1A" and "10A" are smaller than "1B".

    But you can use a more complicated map: std::map<std::pair<int, char>, int> in which key is number and character. Here number will be compared as numbers and characters as characters.

    Use it like:

    std::map<std::pair<int, char>, int> map{{{1, 'B'}, 0}, {{1, 'C'}, 0}};
    

    PS: you can override output like here:

    std::ostream& operator<<(std::ostream& out, const std::map<std::pair<int, char>, int>& map)
    {
        for (const auto& p : map) {
            out << p.first.first << p.first.second << " ";
        }
        return out;
    }
    
    int main() {
        std::map<std::pair<int, char>, int> map{{{1, 'B'}, 0}, {{1, 'C'}, 0}};
    
        std::cout << map;
        return 0;
    }