[boost::transform_iterator] failure with std::vector::const_iterator

Hello! I have an assertion failure using std::vector::const_iterator and boost::transform_iterator. I have a constant seq of constant string pairs delimited by special character (here ':'). My application needs only once to iterate through these pairs and return iterator ranges from the beginning until the colon and after colon until the end. I thought a transform iterator can do the job. I get in the marked position an assertion failure using MSVC 2005 Express Edition. Here the code snippet with problem description: #include <string> #include <vector> #include <utility> #include <functional> #include <boost/iterator/transform_iterator.hpp> #include <boost/range/iterator_range.hpp> #include <boost/utility.hpp> #include <boost/bind.hpp> typedef boost::iterator_range<std::string::const_iterator> iter_range; typedef std::pair<iter_range,iter_range> result_type; struct string_splitter : std::unary_function<std::string const&, result_type> { result_type operator()(std::string const& s)const throw() { iter_range r1(s.begin(), s.begin() + s.find(":")); iter_range r2(r1.end()+1, s.end()); return result_type(r1,r2); } }; typedef std::vector<std::string> str_vector; typedef str_vector::const_iterator vector_citer; typedef boost::transform_iterator<string_splitter, vector_citer> msg_opcode_citer; int main() { //create vector of strings and put 2 strings inside str_vector v; v.push_back(std::string("test1:opcode1")); v.push_back(std::string("test2:opcode2")); //!!!increment operator or dereference operator cause an assertion failure!!! // stating: "vector iterators incompatible" for(msg_opcode_citer curr = msg_opcode_citer(const_cast<str_vector const&>(v).begin(), string_splitter()), end; curr != end; ++curr) { result_type t = *curr; } return 0; } Did I miss something? With Kind Regards, Ovanes Markarian

Ovanes Markarian wrote:
Hello!
I have an assertion failure using std::vector::const_iterator and boost::transform_iterator.
I have a constant seq of constant string pairs delimited by special character (here ':'). My application needs only once to iterate through these pairs and return iterator ranges from the beginning until the colon and after colon until the end. I thought a transform iterator can do the job. I get in the marked position an assertion failure using MSVC 2005 Express Edition.
Here the code snippet with problem description:
#include <string> #include <vector> #include <utility> #include <functional>
#include <boost/iterator/transform_iterator.hpp> #include <boost/range/iterator_range.hpp> #include <boost/utility.hpp> #include <boost/bind.hpp>
typedef boost::iterator_range<std::string::const_iterator> iter_range; typedef std::pair<iter_range,iter_range> result_type;
struct string_splitter : std::unary_function<std::string const&, result_type> { result_type operator()(std::string const& s)const throw() { iter_range r1(s.begin(), s.begin() + s.find(":")); iter_range r2(r1.end()+1, s.end()); return result_type(r1,r2); } };
typedef std::vector<std::string> str_vector; typedef str_vector::const_iterator vector_citer; typedef boost::transform_iterator<string_splitter, vector_citer> msg_opcode_citer;
int main() { //create vector of strings and put 2 strings inside str_vector v; v.push_back(std::string("test1:opcode1")); v.push_back(std::string("test2:opcode2"));
//!!!increment operator or dereference operator cause an assertion failure!!! // stating: "vector iterators incompatible" for(msg_opcode_citer curr = msg_opcode_citer(const_cast<str_vector const&>(v).begin(), string_splitter()), end; curr != end; ++curr) { result_type t = *curr; }
return 0; }
Did I miss something?
'end' seems not initialized. Try.. for(msg_opcode_citer curr = msg_opcode_citer(boost::const_begin(v), string_splitter()), end = msg_opcode_citer(boost::const_end(v), string_splitter()); curr != end; ++curr) { result_type t = *curr; } Regards, -- Shunsuke Sogame

Many thanks that helped ;) Why did not I come up with this... Thanks a lot! Ovanes -----Original Message----- From: shunsuke [mailto:pstade.mb@gmail.com] Sent: Montag, 5. März 2007 03:41 To: boost-users@lists.boost.org Subject: Re: [Boost-users] [boost::transform_iterator] failure withstd::vector::const_iterator Ovanes Markarian wrote:
Hello!
I have an assertion failure using std::vector::const_iterator and boost::transform_iterator.
I have a constant seq of constant string pairs delimited by special character (here ':'). My application needs only once to iterate through these pairs and return iterator ranges from the beginning until the colon and after colon until the end. I thought a transform iterator can do the job. I get in the marked position an assertion failure using MSVC 2005 Express Edition.
Here the code snippet with problem description:
#include <string> #include <vector> #include <utility> #include <functional>
#include <boost/iterator/transform_iterator.hpp> #include <boost/range/iterator_range.hpp> #include <boost/utility.hpp> #include <boost/bind.hpp>
typedef boost::iterator_range<std::string::const_iterator> iter_range; typedef std::pair<iter_range,iter_range> result_type;
struct string_splitter : std::unary_function<std::string const&, result_type> { result_type operator()(std::string const& s)const throw() { iter_range r1(s.begin(), s.begin() + s.find(":")); iter_range r2(r1.end()+1, s.end()); return result_type(r1,r2); } };
typedef std::vector<std::string> str_vector; typedef str_vector::const_iterator vector_citer; typedef boost::transform_iterator<string_splitter, vector_citer> msg_opcode_citer;
int main() { //create vector of strings and put 2 strings inside str_vector v; v.push_back(std::string("test1:opcode1")); v.push_back(std::string("test2:opcode2"));
//!!!increment operator or dereference operator cause an assertion failure!!! // stating: "vector iterators incompatible" for(msg_opcode_citer curr = msg_opcode_citer(const_cast<str_vector const&>(v).begin(), string_splitter()), end; curr != end; ++curr) { result_type t = *curr; }
return 0; }
Did I miss something?
'end' seems not initialized. Try.. for(msg_opcode_citer curr = msg_opcode_citer(boost::const_begin(v), string_splitter()), end = msg_opcode_citer(boost::const_end(v), string_splitter()); curr != end; ++curr) { result_type t = *curr; } Regards, -- Shunsuke Sogame _______________________________________________ Boost-users mailing list Boost-users@lists.boost.org http://lists.boost.org/mailman/listinfo.cgi/boost-users

"Ovanes Markarian" <om_boost@keywallet.com> writes:
Many thanks that helped ;) Why did not I come up with this... Thanks a lot!
You might also look at boost::token_iterator. [And might I suggest that all posters to this thread avoid over-quoting?] -- Dave Abrahams Boost Consulting www.boost-consulting.com
participants (3)
-
David Abrahams
-
Ovanes Markarian
-
shunsuke