stl_iterator_base_funcs.h revision 169691
1139804Simp// Functions used by iterators -*- C++ -*-
24Srgrimes
34Srgrimes// Copyright (C) 2001, 2002, 2003, 2004, 2005, 2006
4235407Savg// Free Software Foundation, Inc.
5235407Savg//
6235407Savg// This file is part of the GNU ISO C++ Library.  This library is free
74Srgrimes// software; you can redistribute it and/or modify it under the
84Srgrimes// terms of the GNU General Public License as published by the
94Srgrimes// Free Software Foundation; either version 2, or (at your option)
104Srgrimes// any later version.
114Srgrimes
124Srgrimes// This library is distributed in the hope that it will be useful,
134Srgrimes// but WITHOUT ANY WARRANTY; without even the implied warranty of
144Srgrimes// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
154Srgrimes// GNU General Public License for more details.
164Srgrimes
174Srgrimes// You should have received a copy of the GNU General Public License along
184Srgrimes// with this library; see the file COPYING.  If not, write to the Free
194Srgrimes// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
204Srgrimes// USA.
214Srgrimes
224Srgrimes// As a special exception, you may use this file as part of a free software
234Srgrimes// library without restriction.  Specifically, if other files instantiate
244Srgrimes// templates or use macros or inline functions from this file, or you compile
254Srgrimes// this file and link it with other files to produce an executable, this
264Srgrimes// file does not by itself cause the resulting executable to be covered by
274Srgrimes// the GNU General Public License.  This exception does not however
284Srgrimes// invalidate any other reasons why the executable file might be covered by
294Srgrimes// the GNU General Public License.
304Srgrimes
314Srgrimes/*
324Srgrimes *
334Srgrimes * Copyright (c) 1994
344Srgrimes * Hewlett-Packard Company
354Srgrimes *
364Srgrimes * Permission to use, copy, modify, distribute and sell this software
37620Srgrimes * and its documentation for any purpose is hereby granted without fee,
384Srgrimes * provided that the above copyright notice appear in all copies and
394Srgrimes * that both that copyright notice and this permission notice appear
40116182Sobrien * in supporting documentation.  Hewlett-Packard Company makes no
41116182Sobrien * representations about the suitability of this software for any
42116182Sobrien * purpose.  It is provided "as is" without express or implied warranty.
4387649Sguido *
4487649Sguido *
452056Swollman * Copyright (c) 1996-1998
461549Srgrimes * Silicon Graphics Computer Systems, Inc.
47163858Sjb *
48163858Sjb * Permission to use, copy, modify, distribute and sell this software
495764Sbde * and its documentation for any purpose is hereby granted without fee,
5056525Sbde * provided that the above copyright notice appear in all copies and
5185448Sjlemon * that both that copyright notice and this permission notice appear
52131931Smarcel * in supporting documentation.  Silicon Graphics makes no
5312675Sjulian * representations about the suitability of this software for any
5485373Sjlemon * purpose.  It is provided "as is" without express or implied warranty.
55116663Siedowse */
5685373Sjlemon
57164033Srwatson/** @file stl_iterator_base_funcs.h
5869929Sobrien *  This is an internal header file, included by other library headers.
5985373Sjlemon *  You should not attempt to use it directly.
6018951Sjulian *
6112701Sphk *  This file contains all of the general iterator-related utility
62174905Swkoszek *  functions, such as distance() and advance().
632056Swollman */
6434924Sbde
6585373Sjlemon#ifndef _ITERATOR_BASE_FUNCS_H
664Srgrimes#define _ITERATOR_BASE_FUNCS_H 1
6787620Sguido
6887620Sguido#pragma GCC system_header
6912701Sphk#include <bits/concept_check.h>
70177642Sphk
714Srgrimes_GLIBCXX_BEGIN_NAMESPACE(std)
72179246Sed
73179246Sed  template<typename _InputIterator>
7485373Sjlemon    inline typename iterator_traits<_InputIterator>::difference_type
7585373Sjlemon    __distance(_InputIterator __first, _InputIterator __last,
7685373Sjlemon               input_iterator_tag)
7785373Sjlemon    {
7885373Sjlemon      // concept requirements
7985373Sjlemon      __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
8085373Sjlemon
8185373Sjlemon      typename iterator_traits<_InputIterator>::difference_type __n = 0;
8285373Sjlemon      while (__first != __last)
8385373Sjlemon	{
8485373Sjlemon	  ++__first;
85125467Skan	  ++__n;
86125467Skan	}
87125467Skan      return __n;
88125467Skan    }
897680Sjoerg
9085373Sjlemon  template<typename _RandomAccessIterator>
91116663Siedowse    inline typename iterator_traits<_RandomAccessIterator>::difference_type
92116663Siedowse    __distance(_RandomAccessIterator __first, _RandomAccessIterator __last,
93116663Siedowse               random_access_iterator_tag)
9487620Sguido    {
9587620Sguido      // concept requirements
9687620Sguido      __glibcxx_function_requires(_RandomAccessIteratorConcept<
97116663Siedowse				  _RandomAccessIterator>)
98163858Sjb      return __last - __first;
99163858Sjb    }
1005764Sbde
101116663Siedowse  /**
10285448Sjlemon   *  @brief A generalization of pointer arithmetic.
103158944Sphk   *  @param  first  An input iterator.
104158944Sphk   *  @param  last  An input iterator.
10578161Speter   *  @return  The distance between them.
10642373Syokota   *
107798Swollman   *  Returns @c n such that first + n == last.  This requires that @p last
10885373Sjlemon   *  must be reachable from @p first.  Note that @c n may be negative.
1094Srgrimes   *
11085373Sjlemon   *  For random access iterators, this uses their @c + and @c - operations
1114Srgrimes   *  and are constant time.  For other %iterator classes they are linear time.
1124Srgrimes  */
11318951Sjulian  template<typename _InputIterator>
11418951Sjulian    inline typename iterator_traits<_InputIterator>::difference_type
11518951Sjulian    distance(_InputIterator __first, _InputIterator __last)
11618951Sjulian    {
11718951Sjulian      // concept requirements -- taken care of in __distance
11818951Sjulian      return std::__distance(__first, __last,
11918951Sjulian			     std::__iterator_category(__first));
12018951Sjulian    }
121138249Sscottl
12285373Sjlemon  template<typename _InputIterator, typename _Distance>
12318951Sjulian    inline void
12485373Sjlemon    __advance(_InputIterator& __i, _Distance __n, input_iterator_tag)
1254Srgrimes    {
12685373Sjlemon      // concept requirements
12785373Sjlemon      __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
12885373Sjlemon      while (__n--)
129101436Sjake	++__i;
130196506Sed    }
131196506Sed
13285373Sjlemon  template<typename _BidirectionalIterator, typename _Distance>
133196506Sed    inline void
13485373Sjlemon    __advance(_BidirectionalIterator& __i, _Distance __n,
13585373Sjlemon	      bidirectional_iterator_tag)
13685373Sjlemon    {
13785373Sjlemon      // concept requirements
13885373Sjlemon      __glibcxx_function_requires(_BidirectionalIteratorConcept<
13985373Sjlemon				  _BidirectionalIterator>)
14085373Sjlemon      if (__n > 0)
14185373Sjlemon        while (__n--)
142196506Sed	  ++__i;
14385373Sjlemon      else
14485373Sjlemon        while (__n++)
14585373Sjlemon	  --__i;
14685373Sjlemon    }
1474Srgrimes
14885373Sjlemon  template<typename _RandomAccessIterator, typename _Distance>
149196506Sed    inline void
15085373Sjlemon    __advance(_RandomAccessIterator& __i, _Distance __n,
15110665Sbde              random_access_iterator_tag)
15287620Sguido    {
15387620Sguido      // concept requirements
1544Srgrimes      __glibcxx_function_requires(_RandomAccessIteratorConcept<
15585373Sjlemon				  _RandomAccessIterator>)
15610665Sbde      __i += __n;
15785373Sjlemon    }
15885373Sjlemon
15985373Sjlemon  /**
16087620Sguido   *  @brief A generalization of pointer arithmetic.
16187620Sguido   *  @param  i  An input iterator.
16287620Sguido   *  @param  n  The "delta" by which to change @p i.
16387620Sguido   *  @return  Nothing.
16487620Sguido   *
16587620Sguido   *  This increments @p i by @p n.  For bidirectional and random access
16685373Sjlemon   *  iterators, @p n may be negative, in which case @p i is decremented.
16785373Sjlemon   *
16885373Sjlemon   *  For random access iterators, this uses their @c + and @c - operations
16985373Sjlemon   *  and are constant time.  For other %iterator classes they are linear time.
17085373Sjlemon  */
17185373Sjlemon  template<typename _InputIterator, typename _Distance>
17285373Sjlemon    inline void
17385373Sjlemon    advance(_InputIterator& __i, _Distance __n)
17485373Sjlemon    {
17585373Sjlemon      // concept requirements -- taken care of in __advance
17685373Sjlemon      typename iterator_traits<_InputIterator>::difference_type __d = __n;
17785373Sjlemon      std::__advance(__i, __d, std::__iterator_category(__i));
17885373Sjlemon    }
17985373Sjlemon
18048104Syokota_GLIBCXX_END_NAMESPACE
18185373Sjlemon
18285373Sjlemon#endif /* _ITERATOR_BASE_FUNCS_H */
18385373Sjlemon