[gil] how does dereference_iterator_adaptor defines it's iterator category?

Hi all, I'm still investigating compilation errors with my gil extension while compiling on MSVC10. I have exchanged boost::random_access_traversal_tag with std::random_access_iterator_tag with all gil iterator types. This solved some of my problems. Some still remain. Here is what I have discovered. When using a boost::gil::kth_channel_view_type with bit_aligned image types I'm running into the same problem I had with just using bit_aligned image types. Now kth_channel_view_type uses a boost::gil::dereference_iterator_adaptor for iteration purposes. This adaptor defines it's iterator category as boost::detail::iterator_category_with_traversal<std::input_iterator_tag,boost::random_access_traversal_tag> which is wrong. I have been trying to figure out where this definition is coming from. But I'm not able to. All occurrences of random_access_traversal_tag have been removed from gil code. Which leads me to believe it's coming from boost itself somewhere. Here is some code displaying the problem. #include <vector> #include <algorithm> #include <boost/gil/gil_all.hpp> using namespace std; using namespace boost; using namespace boost::gil; int main(int argc, char* argv[]) { typedef bit_aligned_image1_type< 1, gray_layout_t >::type image_t; typedef image_t::view_t view_t; typedef view_t::x_iterator view_it_t; typedef view_it_t::iterator_category view_cat_t; // it's std::random_access_iterator_tag view_cat_t view_cat; typedef kth_channel_view_type< 0, view_t >::type plane_t; typedef plane_t::x_iterator plane_it_t; typedef plane_it_t::iterator_category plane_cat_t; // it's boost::detail::iterator_category_with_traversal<std::input_iterator_tag,boost::random_access_traversal_tag> plane_cat_t plane_cat; return 0; } Regards, Christian

Christian Henning <chhenning <at> gmail.com> writes:
dereference_iterator_adaptor uses iterator_adapter with a traversal/category type of boost::use_default. The way use_default behaves is to discover the category/traversal type of the iterator it's adapting (bit_aligned_pixel_iterator<...> in this case), then convert that into a traversal type. In this case, bit_aligned_pixel_iterator has a category of std::random_access_iterator_tag, which gets converted back into boost::random_access_traversal_tag. iterator_adapter then hands off its work to iterator_facade, giving iterator_facade this traversal type instead of the category/traversal type the iterator had originally. iterator_facade then puts its decaying logic into action. In this case it decays from random access into input because of the whole reference vs. proxy object issue, behaving identically to using bit_aligned_pixel_iterator<...> directly with boost::random_access_traversal_tag. The fix in this case is to have dereference_iterator_adaptor forward the wrapped iterator's category to iterator_adaptor rather than pass use_default, so the category doesn't get converted back to a traversal type. Change lines 47 and 53 in pixel_iterator_adaptor.hpp from 'use_default' to 'typename std::iterator_traits<Iterator>::iterator_category'.

Adam Merz <adammerz <at> hotmail.com> writes:
Change lines 47 and 53 in pixel_iterator_adaptor.hpp from 'use_default' to 'typename std::iterator_traits<Iterator>::iterator_category'.
Apologies, lines 47 and 55, not 53.

Hi there,
I could not figure out how this use_default parameter behaves. With your explanation I think the conversion is done inside iterator_adaptor_base class when putting together a iterator_facade type. I think the compile time function ia_dflt_help is doing it. Please correct me when I'm wrong, but this function just compares against use_default and uses either iterator_traversal<Base> in case of use_default or does nothing. Now iterator_traversal<Base> is doing exactly what we are doing it's invoking std::iterator_traits<Iterator> internally. Though, I still don't quite understand where the boost::random_access_traversal_tag is coming from? But at the end of the day I understand your proposed fix and it works. Thanks a lot for your help, Christian
participants (2)
-
Adam Merz
-
Christian Henning