Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why isn't std::next/prev templated by distance like std::advance?

Out of curiosity, what's the rationale to use a template parameter for std::advance()'s distance type, but use the iterator's difference_type for the distance in std::next() and std::prev()?

Why not use the same approach (either one)?

Follow up:

Presence of default n = 1 does not seem to prevent next to be templated by Distance as was suggested in the answer below. This compiles:

#include <iterator>
#include <set>

template<typename InputIt,
    typename Distance = typename std::iterator_traits<InputIt>::difference_type>
InputIt my_next(InputIt it, Distance n = 1)
{
    std::advance(it, n);
    return it;
}

int main()
{
    std::set<int> s;
    my_next(s.begin());
    my_next(s.begin(), 10ul);

    return 0;
}
like image 200
user2052436 Avatar asked Sep 01 '21 23:09

user2052436


1 Answers

It is needed to be able to compile both std::next(it, n) and std::next(it) with default 1:

template<typename InputIt , typename Distance>
InputIt 
next(InputIt it, Distance n = 1)
{
    std::advance(it, n);
    return it;
}

void foo(int *p)
{
    next(p, 1);         // ok
    next<int*, int>(p); // ok
    next(p);  // error: no matching function for call to 'next(int*&)'
}

There is a discussion of possible approaches to this overload resolution issue in gcc bugzilla: https://gcc.gnu.org/bugzilla/show_bug.cgi?id=40497

like image 78
dewaffled Avatar answered Nov 15 '22 01:11

dewaffled