Re: [Boost-bugs] [Boost C++ Libraries] #3659: warning when using boost::counting_iterator<int> and std::vector<int> on MSVC

Subject: Re: [Boost-bugs] [Boost C++ Libraries] #3659: warning when using boost::counting_iterator<int> and std::vector<int> on MSVC
From: Boost C++ Libraries (noreply_at_[hidden])
Date: 2011-06-05 08:06:45


#3659: warning when using boost::counting_iterator<int> and std::vector<int> on
MSVC
---------------------------+------------------------------------------------
  Reporter: anonymous | Owner: dave
      Type: Bugs | Status: closed
 Milestone: Boost 1.42.0 | Component: iterator
   Version: Boost 1.41.0 | Severity: Cosmetic
Resolution: invalid | Keywords:
---------------------------+------------------------------------------------

Comment (by Sergey Mitsyn <svm at jinr.ru>):

 Replying to [comment:5 dave]:
> There's no C-style cast. That's calling numeric_distance from
 boost/detail/numeric_traits.hpp.


 Yes, sorry, I've missed that.

> Otherwise, I think the compiler may be telling you that you're doing
 something you shouldn't do, and this is not a bug in the library.

 IMHO taking a difference between two iterators is not a thing everybody
 shouldn't do, which is the case if {{{ Difference }}} type is specified as
 {{{int}}}. And adding a difference between two iterators to an iterator of
 the same type is not a thing everybody shouldn't do either, which is the
 case with default {{{ Difference }}} type.

 ----

 Ok, i've investigated the problem a little more. The actual problem i'm
 faced is warning in the following code:

 {{{

 typedef boost::counting_iterator<int, boost::use_default> iterator_type;
 //typedef boost::counting_iterator<int,
 boost::bidirectional_traversal_tag> iterator_type;
 iterator_type a(0), b(10);
 std::vector<int> v(10, 0);
 std::copy( a,b,v.begin() );

 }}}

 The actual warning may be reproduced by this code (inside std::copy
 implementation):

 {{{

 std::vector<int>::iterator it = v.begin();
 it += b-a;

 }}}

 The {{{std::allocator<T>::difference_type}}} that is used by
 {{{std::vector}}} is defined as {{{ptrdiff_t}}}, which is {{{int}}} for
 32-bit target. Thus, {{{std::vector::iterator::operator+=}}} has 32-bit
 integer as an argument.

 On the other hand, {{{boost::integer_traits}}} defines
 {{{difference_type}}} to be 64-bit {{{intmax_t}}} if {{{Integer}}} and
 {{{ptrdiff_t}}} are the same size, which is the case. Thus, the return
 type of {{{operator-}}} for {{{boost::counting_iterator}}} is 64-bit
 integer. Passing it to operator+= causes the warning.

 What I'm thinking about now is the fact that Dinkumware used 32-bit
 integer for 32-bit machine architecture instead of 64-bit, thus ignoring
 the requirement to represent any difference, as Steven stated above. Maybe
 Boost could also switch to using 32-bit ptrdiff_t with the same reason as
 Dinkumware does, at least for MSVC?

 ----

 Also the interesting fact is that for
 {{{boost::counting_iterator<short>}}} no warning is shown, because it's
 {{{difference_type}}} is {{{ptrdiff_t}}}. But such workaround is
 unacceptable when there's a need in values bigger than 32767 :(.

-- 
Ticket URL: <https://svn.boost.org/trac/boost/ticket/3659#comment:6>
Boost C++ Libraries <http://www.boost.org/>
Boost provides free peer-reviewed portable C++ source libraries.

This archive was generated by hypermail 2.1.7 : 2017-02-16 18:50:06 UTC