Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How do I output a set used as key for a map?

Tags:

c++

I get this error when I compile this code:

#include <map>
#include <set>
#include <iostream>

int main() {
    using std::set;
    using std::map;

    set<int> s;
    s.insert(4);
    s.insert(3);

    map<set<int>, int> myMap;

    myMap.insert(make_pair(s, 8));

    for (map<set<int>, int>::iterator it = myMap.begin(); it != myMap.end();
            it++) {

        std::cout << it->first << "->" << it->second << std::endl; // HERE
    }
    return 0;
}

The error is from the line marked //HERE:

error: cannot bind std::ostream {aka std::basic_ostream<char>} lvalue to std::basic_ostream<char>&&

like image 487
sherek_66 Avatar asked Jan 27 '26 05:01

sherek_66


1 Answers

Make a stream operator for the key type.

I personally dislike creating the overload in the std namespace, so I create a "manipulator" wrapper:

Live On Coliru

#include <set>
#include <map>
#include <iostream>
#include <iterator>

template <typename T>
struct io {
    io(T const& t) : t(t) {}
  private:
    T const& t;

    friend std::ostream& operator<<(std::ostream& os, io const& o) {
        os << "{ ";
        using namespace std;
        copy(begin(o.t), end(o.t), ostream_iterator<typename T::value_type>(os, " "));
        return os << "}";
    }
};

int main() {  
    using namespace std;
    auto myMap = map<set<int>, int> { { { { 4, 3 }, 8 } } };

    for (auto& [k,v] : myMap)
        std::cout << io{k} << " -> " << v << "\n";
}

Prints

{ 3 4 } -> 8
  • A version just using c++11: http://coliru.stacked-crooked.com/a/bfb571f3e43bda18
  • A version just using c++03: http://coliru.stacked-crooked.com/a/3f28f8f90c386b50 (man that was tedious)
like image 190
sehe Avatar answered Jan 29 '26 19:01

sehe