I'm using std::map in such a way:
#include <map>
#include <string>
#include <iostream>
using namespace std;
int main(int argc, char* argv[])
{
map<string, int> my_map;
my_map.insert(pair<string, int>("Ab", 1));
my_map.insert(pair<string, int>("Abb", 2));
my_map.insert(pair<string, int>("Abc", 3));
my_map.insert(pair<string, int>("Abd", 4));
my_map.insert(pair<string, int>("Ac", 5));
my_map.insert(pair<string, int>("Ad", 5));
cout<<my_map.lower_bound("Ab")->second<<endl;
cout<<my_map.upper_bound("Ab")->second<<endl;
return 0;
}
http://ideone.com/5YPQmj
I'd like to get all values whose key starts with a particular string (for example "Ab"). I can easily get the begin iterator using map::lower_bound. But how can I get an upper bound? Do I have to iterate the whole set starting at lower bound and check every key if it still starts with "Ab"?
I found a similar answer check out this page: (map complex find operation)
Code Exert:
template<typename Map> typename Map::const_iterator
find_prefix(Map const& map, typename Map::key_type const& key)
{
typename Map::const_iterator it = map.upper_bound(key);
while (it != map.begin())
{
--it;
if(key.substr(0, it->first.size()) == it->first)
return it;
}
return map.end(); // map contains no prefix
}
It looks as if in this example you iterate from the upper_bound backwards till the beginning looking for the specific substring
This example is slightly different but should server as a good building block
you can use Boost filter iterator which give you a "begin" and a "end" iterator from normal iterators when they given a predicate (a bool function which says which values to include)
For example:
template <class Predicate>
boost::filter_iterator<Predicate, map<string,int>::const_iterator> begin(Predicate predicate) const
{
return boost::make_filter_iterator(predicate, my_map.begin(), my_map.end());
}
template <class Predicate>
boost::filter_iterator<Predicate, map<string,int>::const_iterator> end(Predicate predicate) const
{
return boost::make_filter_iterator(predicate, my_map.end(), my_map.end());
}
struct isMatch
{
isMatch(const std::string prefix) {m_prefix = prefix;};
bool operator()(std::string value)
{
return value.find_first_of(m_prefix) == 0;
};
std::string m_prefix;
};
//using:
isMatch startWithAb("Ab");
auto myBegin = boost::filter_iterator<startWithAb> begin();
auto myEnd = boost::filter_iterator<startWithAb> end();
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With