No, I'm not. I needed a container which stores two kinds of values, and allows access to one kind of value with the other kind of value, and the map (or multimap) fits that bill.
The bolded statements should not be exclusive to one another. Ideally, a map should allow efficient access by sequential index of the the current key value, i.e. so that you increment the index iterator to access the next key value of the map, and hence, also the mapped value. I was complaining mostly about the syntax necessary to achieve that goal in a map or multimap.Maps and multimaps are not designed for efficient access by sequential index. They are associative containers designed for efficient access by key value. They are not designed for efficient access by mapped value.
Ok, but using that method requires writing your own function for using a generic-type of iterator for a map. There is nothing for that already provided by std::map or std::multimap.For example:
That said, instead of implementing an algorithm, I could have implemented a predicate and used std::find_if, e.g.,Code:template<typename IT, typename T> bool value_exists(IT begin, IT end, const T& value) { for (; begin != end; ++begin) { if (begin->second == value) { return true; } } return false; } #include <map> #include <string> int main() { std::map<std::string, int> x; // ... if (value_exists(x.begin(), x.end(), 123)) { // ... } }
Code:template<typename Pair> class CompareSecond { public: explicit CompareSecond(const typename Pair::second_type& x) : x_(x) {} bool operator()(const Pair& y) const { return y.second == x_; } private: typename Pair::second_type x_; }; #include <algorithm> template<typename IT, typename T> bool value_exists(IT begin, IT end, const T& value) { return std::find_if(begin, end, CompareSecond<typename IT::value_type>(value)) != end; } #include <map> #include <string> int main() { std::map<std::string, int> x; // ... if (value_exists(x.begin(), x.end(), 123)) { // ... } }