annotate DEPENDENCIES/generic/include/boost/operators.hpp @ 133:4acb5d8d80b6 tip

Don't fail environmental check if README.md exists (but .txt and no-suffix don't)
author Chris Cannam
date Tue, 30 Jul 2019 12:25:44 +0100
parents c530137014c0
children
rev   line source
Chris@16 1 // Boost operators.hpp header file ----------------------------------------//
Chris@16 2
Chris@16 3 // (C) Copyright David Abrahams, Jeremy Siek, Daryle Walker 1999-2001.
Chris@16 4 // Distributed under the Boost Software License, Version 1.0. (See
Chris@16 5 // accompanying file LICENSE_1_0.txt or copy at
Chris@16 6 // http://www.boost.org/LICENSE_1_0.txt)
Chris@16 7
Chris@16 8 // See http://www.boost.org/libs/utility/operators.htm for documentation.
Chris@16 9
Chris@16 10 // Revision History
Chris@16 11 // 16 Dec 10 Limit warning suppression for 4284 to older versions of VC++
Chris@16 12 // (Matthew Bradbury, fixes #4432)
Chris@16 13 // 07 Aug 08 Added "euclidean" spelling. (Daniel Frey)
Chris@16 14 // 03 Apr 08 Make sure "convertible to bool" is sufficient
Chris@16 15 // for T::operator<, etc. (Daniel Frey)
Chris@16 16 // 24 May 07 Changed empty_base to depend on T, see
Chris@16 17 // http://svn.boost.org/trac/boost/ticket/979
Chris@16 18 // 21 Oct 02 Modified implementation of operators to allow compilers with a
Chris@16 19 // correct named return value optimization (NRVO) to produce optimal
Chris@16 20 // code. (Daniel Frey)
Chris@16 21 // 02 Dec 01 Bug fixed in random_access_iteratable. (Helmut Zeisel)
Chris@16 22 // 28 Sep 01 Factored out iterator operator groups. (Daryle Walker)
Chris@16 23 // 27 Aug 01 'left' form for non commutative operators added;
Chris@16 24 // additional classes for groups of related operators added;
Chris@16 25 // workaround for empty base class optimization
Chris@16 26 // bug of GCC 3.0 (Helmut Zeisel)
Chris@16 27 // 25 Jun 01 output_iterator_helper changes: removed default template
Chris@16 28 // parameters, added support for self-proxying, additional
Chris@16 29 // documentation and tests (Aleksey Gurtovoy)
Chris@16 30 // 29 May 01 Added operator classes for << and >>. Added input and output
Chris@16 31 // iterator helper classes. Added classes to connect equality and
Chris@16 32 // relational operators. Added classes for groups of related
Chris@16 33 // operators. Reimplemented example operator and iterator helper
Chris@16 34 // classes in terms of the new groups. (Daryle Walker, with help
Chris@16 35 // from Alexy Gurtovoy)
Chris@16 36 // 11 Feb 01 Fixed bugs in the iterator helpers which prevented explicitly
Chris@16 37 // supplied arguments from actually being used (Dave Abrahams)
Chris@16 38 // 04 Jul 00 Fixed NO_OPERATORS_IN_NAMESPACE bugs, major cleanup and
Chris@16 39 // refactoring of compiler workarounds, additional documentation
Chris@16 40 // (Alexy Gurtovoy and Mark Rodgers with some help and prompting from
Chris@16 41 // Dave Abrahams)
Chris@16 42 // 28 Jun 00 General cleanup and integration of bugfixes from Mark Rodgers and
Chris@16 43 // Jeremy Siek (Dave Abrahams)
Chris@16 44 // 20 Jun 00 Changes to accommodate Borland C++Builder 4 and Borland C++ 5.5
Chris@16 45 // (Mark Rodgers)
Chris@16 46 // 20 Jun 00 Minor fixes to the prior revision (Aleksey Gurtovoy)
Chris@16 47 // 10 Jun 00 Support for the base class chaining technique was added
Chris@16 48 // (Aleksey Gurtovoy). See documentation and the comments below
Chris@16 49 // for the details.
Chris@16 50 // 12 Dec 99 Initial version with iterator operators (Jeremy Siek)
Chris@16 51 // 18 Nov 99 Change name "divideable" to "dividable", remove unnecessary
Chris@16 52 // specializations of dividable, subtractable, modable (Ed Brey)
Chris@16 53 // 17 Nov 99 Add comments (Beman Dawes)
Chris@16 54 // Remove unnecessary specialization of operators<> (Ed Brey)
Chris@16 55 // 15 Nov 99 Fix less_than_comparable<T,U> second operand type for first two
Chris@16 56 // operators.(Beman Dawes)
Chris@16 57 // 12 Nov 99 Add operators templates (Ed Brey)
Chris@16 58 // 11 Nov 99 Add single template parameter version for compilers without
Chris@16 59 // partial specialization (Beman Dawes)
Chris@16 60 // 10 Nov 99 Initial version
Chris@16 61
Chris@16 62 // 10 Jun 00:
Chris@16 63 // An additional optional template parameter was added to most of
Chris@16 64 // operator templates to support the base class chaining technique (see
Chris@16 65 // documentation for the details). Unfortunately, a straightforward
Chris@16 66 // implementation of this change would have broken compatibility with the
Chris@16 67 // previous version of the library by making it impossible to use the same
Chris@16 68 // template name (e.g. 'addable') for both the 1- and 2-argument versions of
Chris@16 69 // an operator template. This implementation solves the backward-compatibility
Chris@16 70 // issue at the cost of some simplicity.
Chris@16 71 //
Chris@16 72 // One of the complications is an existence of special auxiliary class template
Chris@16 73 // 'is_chained_base<>' (see 'detail' namespace below), which is used
Chris@16 74 // to determine whether its template parameter is a library's operator template
Chris@16 75 // or not. You have to specialize 'is_chained_base<>' for each new
Chris@16 76 // operator template you add to the library.
Chris@16 77 //
Chris@16 78 // However, most of the non-trivial implementation details are hidden behind
Chris@16 79 // several local macros defined below, and as soon as you understand them,
Chris@16 80 // you understand the whole library implementation.
Chris@16 81
Chris@16 82 #ifndef BOOST_OPERATORS_HPP
Chris@16 83 #define BOOST_OPERATORS_HPP
Chris@16 84
Chris@16 85 #include <boost/config.hpp>
Chris@16 86 #include <boost/iterator.hpp>
Chris@16 87 #include <boost/detail/workaround.hpp>
Chris@16 88
Chris@16 89 #if defined(__sgi) && !defined(__GNUC__)
Chris@16 90 # pragma set woff 1234
Chris@16 91 #endif
Chris@16 92
Chris@16 93 #if BOOST_WORKAROUND(BOOST_MSVC, < 1600)
Chris@16 94 # pragma warning( disable : 4284 ) // complaint about return type of
Chris@16 95 #endif // operator-> not begin a UDT
Chris@16 96
Chris@16 97 namespace boost {
Chris@16 98 namespace detail {
Chris@16 99
Chris@101 100 template <typename T> class empty_base {};
Chris@16 101
Chris@16 102 } // namespace detail
Chris@16 103 } // namespace boost
Chris@16 104
Chris@16 105 // In this section we supply the xxxx1 and xxxx2 forms of the operator
Chris@16 106 // templates, which are explicitly targeted at the 1-type-argument and
Chris@16 107 // 2-type-argument operator forms, respectively. Some compilers get confused
Chris@16 108 // when inline friend functions are overloaded in namespaces other than the
Chris@16 109 // global namespace. When BOOST_NO_OPERATORS_IN_NAMESPACE is defined, all of
Chris@16 110 // these templates must go in the global namespace.
Chris@16 111
Chris@16 112 #ifndef BOOST_NO_OPERATORS_IN_NAMESPACE
Chris@16 113 namespace boost
Chris@16 114 {
Chris@16 115 #endif
Chris@16 116
Chris@16 117 // Basic operator classes (contributed by Dave Abrahams) ------------------//
Chris@16 118
Chris@16 119 // Note that friend functions defined in a class are implicitly inline.
Chris@16 120 // See the C++ std, 11.4 [class.friend] paragraph 5
Chris@16 121
Chris@16 122 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 123 struct less_than_comparable2 : B
Chris@16 124 {
Chris@16 125 friend bool operator<=(const T& x, const U& y) { return !static_cast<bool>(x > y); }
Chris@16 126 friend bool operator>=(const T& x, const U& y) { return !static_cast<bool>(x < y); }
Chris@16 127 friend bool operator>(const U& x, const T& y) { return y < x; }
Chris@16 128 friend bool operator<(const U& x, const T& y) { return y > x; }
Chris@16 129 friend bool operator<=(const U& x, const T& y) { return !static_cast<bool>(y < x); }
Chris@16 130 friend bool operator>=(const U& x, const T& y) { return !static_cast<bool>(y > x); }
Chris@16 131 };
Chris@16 132
Chris@16 133 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 134 struct less_than_comparable1 : B
Chris@16 135 {
Chris@16 136 friend bool operator>(const T& x, const T& y) { return y < x; }
Chris@16 137 friend bool operator<=(const T& x, const T& y) { return !static_cast<bool>(y < x); }
Chris@16 138 friend bool operator>=(const T& x, const T& y) { return !static_cast<bool>(x < y); }
Chris@16 139 };
Chris@16 140
Chris@16 141 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 142 struct equality_comparable2 : B
Chris@16 143 {
Chris@16 144 friend bool operator==(const U& y, const T& x) { return x == y; }
Chris@16 145 friend bool operator!=(const U& y, const T& x) { return !static_cast<bool>(x == y); }
Chris@16 146 friend bool operator!=(const T& y, const U& x) { return !static_cast<bool>(y == x); }
Chris@16 147 };
Chris@16 148
Chris@16 149 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 150 struct equality_comparable1 : B
Chris@16 151 {
Chris@16 152 friend bool operator!=(const T& x, const T& y) { return !static_cast<bool>(x == y); }
Chris@16 153 };
Chris@16 154
Chris@16 155 // A macro which produces "name_2left" from "name".
Chris@16 156 #define BOOST_OPERATOR2_LEFT(name) name##2##_##left
Chris@16 157
Chris@16 158 // NRVO-friendly implementation (contributed by Daniel Frey) ---------------//
Chris@16 159
Chris@16 160 #if defined(BOOST_HAS_NRVO) || defined(BOOST_FORCE_SYMMETRIC_OPERATORS)
Chris@16 161
Chris@16 162 // This is the optimal implementation for ISO/ANSI C++,
Chris@16 163 // but it requires the compiler to implement the NRVO.
Chris@16 164 // If the compiler has no NRVO, this is the best symmetric
Chris@16 165 // implementation available.
Chris@16 166
Chris@16 167 #define BOOST_BINARY_OPERATOR_COMMUTATIVE( NAME, OP ) \
Chris@16 168 template <class T, class U, class B = ::boost::detail::empty_base<T> > \
Chris@16 169 struct NAME##2 : B \
Chris@16 170 { \
Chris@16 171 friend T operator OP( const T& lhs, const U& rhs ) \
Chris@16 172 { T nrv( lhs ); nrv OP##= rhs; return nrv; } \
Chris@16 173 friend T operator OP( const U& lhs, const T& rhs ) \
Chris@16 174 { T nrv( rhs ); nrv OP##= lhs; return nrv; } \
Chris@16 175 }; \
Chris@16 176 \
Chris@16 177 template <class T, class B = ::boost::detail::empty_base<T> > \
Chris@16 178 struct NAME##1 : B \
Chris@16 179 { \
Chris@16 180 friend T operator OP( const T& lhs, const T& rhs ) \
Chris@16 181 { T nrv( lhs ); nrv OP##= rhs; return nrv; } \
Chris@16 182 };
Chris@16 183
Chris@16 184 #define BOOST_BINARY_OPERATOR_NON_COMMUTATIVE( NAME, OP ) \
Chris@16 185 template <class T, class U, class B = ::boost::detail::empty_base<T> > \
Chris@16 186 struct NAME##2 : B \
Chris@16 187 { \
Chris@16 188 friend T operator OP( const T& lhs, const U& rhs ) \
Chris@16 189 { T nrv( lhs ); nrv OP##= rhs; return nrv; } \
Chris@16 190 }; \
Chris@16 191 \
Chris@16 192 template <class T, class U, class B = ::boost::detail::empty_base<T> > \
Chris@16 193 struct BOOST_OPERATOR2_LEFT(NAME) : B \
Chris@16 194 { \
Chris@16 195 friend T operator OP( const U& lhs, const T& rhs ) \
Chris@16 196 { T nrv( lhs ); nrv OP##= rhs; return nrv; } \
Chris@16 197 }; \
Chris@16 198 \
Chris@16 199 template <class T, class B = ::boost::detail::empty_base<T> > \
Chris@16 200 struct NAME##1 : B \
Chris@16 201 { \
Chris@16 202 friend T operator OP( const T& lhs, const T& rhs ) \
Chris@16 203 { T nrv( lhs ); nrv OP##= rhs; return nrv; } \
Chris@16 204 };
Chris@16 205
Chris@16 206 #else // defined(BOOST_HAS_NRVO) || defined(BOOST_FORCE_SYMMETRIC_OPERATORS)
Chris@16 207
Chris@16 208 // For compilers without NRVO the following code is optimal, but not
Chris@16 209 // symmetric! Note that the implementation of
Chris@16 210 // BOOST_OPERATOR2_LEFT(NAME) only looks cool, but doesn't provide
Chris@16 211 // optimization opportunities to the compiler :)
Chris@16 212
Chris@16 213 #define BOOST_BINARY_OPERATOR_COMMUTATIVE( NAME, OP ) \
Chris@16 214 template <class T, class U, class B = ::boost::detail::empty_base<T> > \
Chris@16 215 struct NAME##2 : B \
Chris@16 216 { \
Chris@16 217 friend T operator OP( T lhs, const U& rhs ) { return lhs OP##= rhs; } \
Chris@16 218 friend T operator OP( const U& lhs, T rhs ) { return rhs OP##= lhs; } \
Chris@16 219 }; \
Chris@16 220 \
Chris@16 221 template <class T, class B = ::boost::detail::empty_base<T> > \
Chris@16 222 struct NAME##1 : B \
Chris@16 223 { \
Chris@16 224 friend T operator OP( T lhs, const T& rhs ) { return lhs OP##= rhs; } \
Chris@16 225 };
Chris@16 226
Chris@16 227 #define BOOST_BINARY_OPERATOR_NON_COMMUTATIVE( NAME, OP ) \
Chris@16 228 template <class T, class U, class B = ::boost::detail::empty_base<T> > \
Chris@16 229 struct NAME##2 : B \
Chris@16 230 { \
Chris@16 231 friend T operator OP( T lhs, const U& rhs ) { return lhs OP##= rhs; } \
Chris@16 232 }; \
Chris@16 233 \
Chris@16 234 template <class T, class U, class B = ::boost::detail::empty_base<T> > \
Chris@16 235 struct BOOST_OPERATOR2_LEFT(NAME) : B \
Chris@16 236 { \
Chris@16 237 friend T operator OP( const U& lhs, const T& rhs ) \
Chris@16 238 { return T( lhs ) OP##= rhs; } \
Chris@16 239 }; \
Chris@16 240 \
Chris@16 241 template <class T, class B = ::boost::detail::empty_base<T> > \
Chris@16 242 struct NAME##1 : B \
Chris@16 243 { \
Chris@16 244 friend T operator OP( T lhs, const T& rhs ) { return lhs OP##= rhs; } \
Chris@16 245 };
Chris@16 246
Chris@16 247 #endif // defined(BOOST_HAS_NRVO) || defined(BOOST_FORCE_SYMMETRIC_OPERATORS)
Chris@16 248
Chris@16 249 BOOST_BINARY_OPERATOR_COMMUTATIVE( multipliable, * )
Chris@16 250 BOOST_BINARY_OPERATOR_COMMUTATIVE( addable, + )
Chris@16 251 BOOST_BINARY_OPERATOR_NON_COMMUTATIVE( subtractable, - )
Chris@16 252 BOOST_BINARY_OPERATOR_NON_COMMUTATIVE( dividable, / )
Chris@16 253 BOOST_BINARY_OPERATOR_NON_COMMUTATIVE( modable, % )
Chris@16 254 BOOST_BINARY_OPERATOR_COMMUTATIVE( xorable, ^ )
Chris@16 255 BOOST_BINARY_OPERATOR_COMMUTATIVE( andable, & )
Chris@16 256 BOOST_BINARY_OPERATOR_COMMUTATIVE( orable, | )
Chris@16 257
Chris@16 258 #undef BOOST_BINARY_OPERATOR_COMMUTATIVE
Chris@16 259 #undef BOOST_BINARY_OPERATOR_NON_COMMUTATIVE
Chris@16 260 #undef BOOST_OPERATOR2_LEFT
Chris@16 261
Chris@16 262 // incrementable and decrementable contributed by Jeremy Siek
Chris@16 263
Chris@16 264 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 265 struct incrementable : B
Chris@16 266 {
Chris@16 267 friend T operator++(T& x, int)
Chris@16 268 {
Chris@16 269 incrementable_type nrv(x);
Chris@16 270 ++x;
Chris@16 271 return nrv;
Chris@16 272 }
Chris@16 273 private: // The use of this typedef works around a Borland bug
Chris@16 274 typedef T incrementable_type;
Chris@16 275 };
Chris@16 276
Chris@16 277 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 278 struct decrementable : B
Chris@16 279 {
Chris@16 280 friend T operator--(T& x, int)
Chris@16 281 {
Chris@16 282 decrementable_type nrv(x);
Chris@16 283 --x;
Chris@16 284 return nrv;
Chris@16 285 }
Chris@16 286 private: // The use of this typedef works around a Borland bug
Chris@16 287 typedef T decrementable_type;
Chris@16 288 };
Chris@16 289
Chris@16 290 // Iterator operator classes (contributed by Jeremy Siek) ------------------//
Chris@16 291
Chris@16 292 template <class T, class P, class B = ::boost::detail::empty_base<T> >
Chris@16 293 struct dereferenceable : B
Chris@16 294 {
Chris@16 295 P operator->() const
Chris@16 296 {
Chris@16 297 return &*static_cast<const T&>(*this);
Chris@16 298 }
Chris@16 299 };
Chris@16 300
Chris@16 301 template <class T, class I, class R, class B = ::boost::detail::empty_base<T> >
Chris@16 302 struct indexable : B
Chris@16 303 {
Chris@16 304 R operator[](I n) const
Chris@16 305 {
Chris@16 306 return *(static_cast<const T&>(*this) + n);
Chris@16 307 }
Chris@16 308 };
Chris@16 309
Chris@16 310 // More operator classes (contributed by Daryle Walker) --------------------//
Chris@16 311 // (NRVO-friendly implementation contributed by Daniel Frey) ---------------//
Chris@16 312
Chris@16 313 #if defined(BOOST_HAS_NRVO) || defined(BOOST_FORCE_SYMMETRIC_OPERATORS)
Chris@16 314
Chris@16 315 #define BOOST_BINARY_OPERATOR( NAME, OP ) \
Chris@16 316 template <class T, class U, class B = ::boost::detail::empty_base<T> > \
Chris@16 317 struct NAME##2 : B \
Chris@16 318 { \
Chris@16 319 friend T operator OP( const T& lhs, const U& rhs ) \
Chris@16 320 { T nrv( lhs ); nrv OP##= rhs; return nrv; } \
Chris@16 321 }; \
Chris@16 322 \
Chris@16 323 template <class T, class B = ::boost::detail::empty_base<T> > \
Chris@16 324 struct NAME##1 : B \
Chris@16 325 { \
Chris@16 326 friend T operator OP( const T& lhs, const T& rhs ) \
Chris@16 327 { T nrv( lhs ); nrv OP##= rhs; return nrv; } \
Chris@16 328 };
Chris@16 329
Chris@16 330 #else // defined(BOOST_HAS_NRVO) || defined(BOOST_FORCE_SYMMETRIC_OPERATORS)
Chris@16 331
Chris@16 332 #define BOOST_BINARY_OPERATOR( NAME, OP ) \
Chris@16 333 template <class T, class U, class B = ::boost::detail::empty_base<T> > \
Chris@16 334 struct NAME##2 : B \
Chris@16 335 { \
Chris@16 336 friend T operator OP( T lhs, const U& rhs ) { return lhs OP##= rhs; } \
Chris@16 337 }; \
Chris@16 338 \
Chris@16 339 template <class T, class B = ::boost::detail::empty_base<T> > \
Chris@16 340 struct NAME##1 : B \
Chris@16 341 { \
Chris@16 342 friend T operator OP( T lhs, const T& rhs ) { return lhs OP##= rhs; } \
Chris@16 343 };
Chris@16 344
Chris@16 345 #endif // defined(BOOST_HAS_NRVO) || defined(BOOST_FORCE_SYMMETRIC_OPERATORS)
Chris@16 346
Chris@16 347 BOOST_BINARY_OPERATOR( left_shiftable, << )
Chris@16 348 BOOST_BINARY_OPERATOR( right_shiftable, >> )
Chris@16 349
Chris@16 350 #undef BOOST_BINARY_OPERATOR
Chris@16 351
Chris@16 352 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 353 struct equivalent2 : B
Chris@16 354 {
Chris@16 355 friend bool operator==(const T& x, const U& y)
Chris@16 356 {
Chris@16 357 return !static_cast<bool>(x < y) && !static_cast<bool>(x > y);
Chris@16 358 }
Chris@16 359 };
Chris@16 360
Chris@16 361 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 362 struct equivalent1 : B
Chris@16 363 {
Chris@16 364 friend bool operator==(const T&x, const T&y)
Chris@16 365 {
Chris@16 366 return !static_cast<bool>(x < y) && !static_cast<bool>(y < x);
Chris@16 367 }
Chris@16 368 };
Chris@16 369
Chris@16 370 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 371 struct partially_ordered2 : B
Chris@16 372 {
Chris@16 373 friend bool operator<=(const T& x, const U& y)
Chris@16 374 { return static_cast<bool>(x < y) || static_cast<bool>(x == y); }
Chris@16 375 friend bool operator>=(const T& x, const U& y)
Chris@16 376 { return static_cast<bool>(x > y) || static_cast<bool>(x == y); }
Chris@16 377 friend bool operator>(const U& x, const T& y)
Chris@16 378 { return y < x; }
Chris@16 379 friend bool operator<(const U& x, const T& y)
Chris@16 380 { return y > x; }
Chris@16 381 friend bool operator<=(const U& x, const T& y)
Chris@16 382 { return static_cast<bool>(y > x) || static_cast<bool>(y == x); }
Chris@16 383 friend bool operator>=(const U& x, const T& y)
Chris@16 384 { return static_cast<bool>(y < x) || static_cast<bool>(y == x); }
Chris@16 385 };
Chris@16 386
Chris@16 387 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 388 struct partially_ordered1 : B
Chris@16 389 {
Chris@16 390 friend bool operator>(const T& x, const T& y)
Chris@16 391 { return y < x; }
Chris@16 392 friend bool operator<=(const T& x, const T& y)
Chris@16 393 { return static_cast<bool>(x < y) || static_cast<bool>(x == y); }
Chris@16 394 friend bool operator>=(const T& x, const T& y)
Chris@16 395 { return static_cast<bool>(y < x) || static_cast<bool>(x == y); }
Chris@16 396 };
Chris@16 397
Chris@16 398 // Combined operator classes (contributed by Daryle Walker) ----------------//
Chris@16 399
Chris@16 400 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 401 struct totally_ordered2
Chris@16 402 : less_than_comparable2<T, U
Chris@16 403 , equality_comparable2<T, U, B
Chris@16 404 > > {};
Chris@16 405
Chris@16 406 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 407 struct totally_ordered1
Chris@16 408 : less_than_comparable1<T
Chris@16 409 , equality_comparable1<T, B
Chris@16 410 > > {};
Chris@16 411
Chris@16 412 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 413 struct additive2
Chris@16 414 : addable2<T, U
Chris@16 415 , subtractable2<T, U, B
Chris@16 416 > > {};
Chris@16 417
Chris@16 418 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 419 struct additive1
Chris@16 420 : addable1<T
Chris@16 421 , subtractable1<T, B
Chris@16 422 > > {};
Chris@16 423
Chris@16 424 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 425 struct multiplicative2
Chris@16 426 : multipliable2<T, U
Chris@16 427 , dividable2<T, U, B
Chris@16 428 > > {};
Chris@16 429
Chris@16 430 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 431 struct multiplicative1
Chris@16 432 : multipliable1<T
Chris@16 433 , dividable1<T, B
Chris@16 434 > > {};
Chris@16 435
Chris@16 436 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 437 struct integer_multiplicative2
Chris@16 438 : multiplicative2<T, U
Chris@16 439 , modable2<T, U, B
Chris@16 440 > > {};
Chris@16 441
Chris@16 442 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 443 struct integer_multiplicative1
Chris@16 444 : multiplicative1<T
Chris@16 445 , modable1<T, B
Chris@16 446 > > {};
Chris@16 447
Chris@16 448 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 449 struct arithmetic2
Chris@16 450 : additive2<T, U
Chris@16 451 , multiplicative2<T, U, B
Chris@16 452 > > {};
Chris@16 453
Chris@16 454 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 455 struct arithmetic1
Chris@16 456 : additive1<T
Chris@16 457 , multiplicative1<T, B
Chris@16 458 > > {};
Chris@16 459
Chris@16 460 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 461 struct integer_arithmetic2
Chris@16 462 : additive2<T, U
Chris@16 463 , integer_multiplicative2<T, U, B
Chris@16 464 > > {};
Chris@16 465
Chris@16 466 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 467 struct integer_arithmetic1
Chris@16 468 : additive1<T
Chris@16 469 , integer_multiplicative1<T, B
Chris@16 470 > > {};
Chris@16 471
Chris@16 472 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 473 struct bitwise2
Chris@16 474 : xorable2<T, U
Chris@16 475 , andable2<T, U
Chris@16 476 , orable2<T, U, B
Chris@16 477 > > > {};
Chris@16 478
Chris@16 479 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 480 struct bitwise1
Chris@16 481 : xorable1<T
Chris@16 482 , andable1<T
Chris@16 483 , orable1<T, B
Chris@16 484 > > > {};
Chris@16 485
Chris@16 486 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 487 struct unit_steppable
Chris@16 488 : incrementable<T
Chris@16 489 , decrementable<T, B
Chris@16 490 > > {};
Chris@16 491
Chris@16 492 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 493 struct shiftable2
Chris@16 494 : left_shiftable2<T, U
Chris@16 495 , right_shiftable2<T, U, B
Chris@16 496 > > {};
Chris@16 497
Chris@16 498 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 499 struct shiftable1
Chris@16 500 : left_shiftable1<T
Chris@16 501 , right_shiftable1<T, B
Chris@16 502 > > {};
Chris@16 503
Chris@16 504 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 505 struct ring_operators2
Chris@16 506 : additive2<T, U
Chris@16 507 , subtractable2_left<T, U
Chris@16 508 , multipliable2<T, U, B
Chris@16 509 > > > {};
Chris@16 510
Chris@16 511 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 512 struct ring_operators1
Chris@16 513 : additive1<T
Chris@16 514 , multipliable1<T, B
Chris@16 515 > > {};
Chris@16 516
Chris@16 517 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 518 struct ordered_ring_operators2
Chris@16 519 : ring_operators2<T, U
Chris@16 520 , totally_ordered2<T, U, B
Chris@16 521 > > {};
Chris@16 522
Chris@16 523 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 524 struct ordered_ring_operators1
Chris@16 525 : ring_operators1<T
Chris@16 526 , totally_ordered1<T, B
Chris@16 527 > > {};
Chris@16 528
Chris@16 529 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 530 struct field_operators2
Chris@16 531 : ring_operators2<T, U
Chris@16 532 , dividable2<T, U
Chris@16 533 , dividable2_left<T, U, B
Chris@16 534 > > > {};
Chris@16 535
Chris@16 536 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 537 struct field_operators1
Chris@16 538 : ring_operators1<T
Chris@16 539 , dividable1<T, B
Chris@16 540 > > {};
Chris@16 541
Chris@16 542 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 543 struct ordered_field_operators2
Chris@16 544 : field_operators2<T, U
Chris@16 545 , totally_ordered2<T, U, B
Chris@16 546 > > {};
Chris@16 547
Chris@16 548 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 549 struct ordered_field_operators1
Chris@16 550 : field_operators1<T
Chris@16 551 , totally_ordered1<T, B
Chris@16 552 > > {};
Chris@16 553
Chris@16 554 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 555 struct euclidian_ring_operators2
Chris@16 556 : ring_operators2<T, U
Chris@16 557 , dividable2<T, U
Chris@16 558 , dividable2_left<T, U
Chris@16 559 , modable2<T, U
Chris@16 560 , modable2_left<T, U, B
Chris@16 561 > > > > > {};
Chris@16 562
Chris@16 563 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 564 struct euclidian_ring_operators1
Chris@16 565 : ring_operators1<T
Chris@16 566 , dividable1<T
Chris@16 567 , modable1<T, B
Chris@16 568 > > > {};
Chris@16 569
Chris@16 570 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 571 struct ordered_euclidian_ring_operators2
Chris@16 572 : totally_ordered2<T, U
Chris@16 573 , euclidian_ring_operators2<T, U, B
Chris@16 574 > > {};
Chris@16 575
Chris@16 576 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 577 struct ordered_euclidian_ring_operators1
Chris@16 578 : totally_ordered1<T
Chris@16 579 , euclidian_ring_operators1<T, B
Chris@16 580 > > {};
Chris@16 581
Chris@16 582 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 583 struct euclidean_ring_operators2
Chris@16 584 : ring_operators2<T, U
Chris@16 585 , dividable2<T, U
Chris@16 586 , dividable2_left<T, U
Chris@16 587 , modable2<T, U
Chris@16 588 , modable2_left<T, U, B
Chris@16 589 > > > > > {};
Chris@16 590
Chris@16 591 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 592 struct euclidean_ring_operators1
Chris@16 593 : ring_operators1<T
Chris@16 594 , dividable1<T
Chris@16 595 , modable1<T, B
Chris@16 596 > > > {};
Chris@16 597
Chris@16 598 template <class T, class U, class B = ::boost::detail::empty_base<T> >
Chris@16 599 struct ordered_euclidean_ring_operators2
Chris@16 600 : totally_ordered2<T, U
Chris@16 601 , euclidean_ring_operators2<T, U, B
Chris@16 602 > > {};
Chris@16 603
Chris@16 604 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 605 struct ordered_euclidean_ring_operators1
Chris@16 606 : totally_ordered1<T
Chris@16 607 , euclidean_ring_operators1<T, B
Chris@16 608 > > {};
Chris@16 609
Chris@16 610 template <class T, class P, class B = ::boost::detail::empty_base<T> >
Chris@16 611 struct input_iteratable
Chris@16 612 : equality_comparable1<T
Chris@16 613 , incrementable<T
Chris@16 614 , dereferenceable<T, P, B
Chris@16 615 > > > {};
Chris@16 616
Chris@16 617 template <class T, class B = ::boost::detail::empty_base<T> >
Chris@16 618 struct output_iteratable
Chris@16 619 : incrementable<T, B
Chris@16 620 > {};
Chris@16 621
Chris@16 622 template <class T, class P, class B = ::boost::detail::empty_base<T> >
Chris@16 623 struct forward_iteratable
Chris@16 624 : input_iteratable<T, P, B
Chris@16 625 > {};
Chris@16 626
Chris@16 627 template <class T, class P, class B = ::boost::detail::empty_base<T> >
Chris@16 628 struct bidirectional_iteratable
Chris@16 629 : forward_iteratable<T, P
Chris@16 630 , decrementable<T, B
Chris@16 631 > > {};
Chris@16 632
Chris@16 633 // To avoid repeated derivation from equality_comparable,
Chris@16 634 // which is an indirect base class of bidirectional_iterable,
Chris@16 635 // random_access_iteratable must not be derived from totally_ordered1
Chris@16 636 // but from less_than_comparable1 only. (Helmut Zeisel, 02-Dec-2001)
Chris@16 637 template <class T, class P, class D, class R, class B = ::boost::detail::empty_base<T> >
Chris@16 638 struct random_access_iteratable
Chris@16 639 : bidirectional_iteratable<T, P
Chris@16 640 , less_than_comparable1<T
Chris@16 641 , additive2<T, D
Chris@16 642 , indexable<T, D, R, B
Chris@16 643 > > > > {};
Chris@16 644
Chris@16 645 #ifndef BOOST_NO_OPERATORS_IN_NAMESPACE
Chris@16 646 } // namespace boost
Chris@16 647 #endif // BOOST_NO_OPERATORS_IN_NAMESPACE
Chris@16 648
Chris@16 649
Chris@16 650 // BOOST_IMPORT_TEMPLATE1 .. BOOST_IMPORT_TEMPLATE4 -
Chris@16 651 //
Chris@16 652 // When BOOST_NO_OPERATORS_IN_NAMESPACE is defined we need a way to import an
Chris@16 653 // operator template into the boost namespace. BOOST_IMPORT_TEMPLATE1 is used
Chris@16 654 // for one-argument forms of operator templates; BOOST_IMPORT_TEMPLATE2 for
Chris@16 655 // two-argument forms. Note that these macros expect to be invoked from within
Chris@16 656 // boost.
Chris@16 657
Chris@16 658 #ifndef BOOST_NO_OPERATORS_IN_NAMESPACE
Chris@16 659
Chris@16 660 // The template is already in boost so we have nothing to do.
Chris@16 661 # define BOOST_IMPORT_TEMPLATE4(template_name)
Chris@16 662 # define BOOST_IMPORT_TEMPLATE3(template_name)
Chris@16 663 # define BOOST_IMPORT_TEMPLATE2(template_name)
Chris@16 664 # define BOOST_IMPORT_TEMPLATE1(template_name)
Chris@16 665
Chris@16 666 #else // BOOST_NO_OPERATORS_IN_NAMESPACE
Chris@16 667
Chris@16 668 # ifndef BOOST_NO_USING_TEMPLATE
Chris@16 669
Chris@16 670 // Bring the names in with a using-declaration
Chris@16 671 // to avoid stressing the compiler.
Chris@16 672 # define BOOST_IMPORT_TEMPLATE4(template_name) using ::template_name;
Chris@16 673 # define BOOST_IMPORT_TEMPLATE3(template_name) using ::template_name;
Chris@16 674 # define BOOST_IMPORT_TEMPLATE2(template_name) using ::template_name;
Chris@16 675 # define BOOST_IMPORT_TEMPLATE1(template_name) using ::template_name;
Chris@16 676
Chris@16 677 # else
Chris@16 678
Chris@16 679 // Otherwise, because a Borland C++ 5.5 bug prevents a using declaration
Chris@16 680 // from working, we are forced to use inheritance for that compiler.
Chris@16 681 # define BOOST_IMPORT_TEMPLATE4(template_name) \
Chris@16 682 template <class T, class U, class V, class W, class B = ::boost::detail::empty_base<T> > \
Chris@16 683 struct template_name : ::template_name<T, U, V, W, B> {};
Chris@16 684
Chris@16 685 # define BOOST_IMPORT_TEMPLATE3(template_name) \
Chris@16 686 template <class T, class U, class V, class B = ::boost::detail::empty_base<T> > \
Chris@16 687 struct template_name : ::template_name<T, U, V, B> {};
Chris@16 688
Chris@16 689 # define BOOST_IMPORT_TEMPLATE2(template_name) \
Chris@16 690 template <class T, class U, class B = ::boost::detail::empty_base<T> > \
Chris@16 691 struct template_name : ::template_name<T, U, B> {};
Chris@16 692
Chris@16 693 # define BOOST_IMPORT_TEMPLATE1(template_name) \
Chris@16 694 template <class T, class B = ::boost::detail::empty_base<T> > \
Chris@16 695 struct template_name : ::template_name<T, B> {};
Chris@16 696
Chris@16 697 # endif // BOOST_NO_USING_TEMPLATE
Chris@16 698
Chris@16 699 #endif // BOOST_NO_OPERATORS_IN_NAMESPACE
Chris@16 700
Chris@16 701 //
Chris@16 702 // Here's where we put it all together, defining the xxxx forms of the templates
Chris@16 703 // in namespace boost. We also define specializations of is_chained_base<> for
Chris@16 704 // the xxxx, xxxx1, and xxxx2 templates, importing them into boost:: as
Chris@16 705 // necessary.
Chris@16 706 //
Chris@16 707
Chris@16 708 // is_chained_base<> - a traits class used to distinguish whether an operator
Chris@16 709 // template argument is being used for base class chaining, or is specifying a
Chris@16 710 // 2nd argument type.
Chris@16 711
Chris@16 712 namespace boost {
Chris@16 713 // A type parameter is used instead of a plain bool because Borland's compiler
Chris@16 714 // didn't cope well with the more obvious non-type template parameter.
Chris@16 715 namespace detail {
Chris@16 716 struct true_t {};
Chris@16 717 struct false_t {};
Chris@16 718 } // namespace detail
Chris@16 719
Chris@16 720 // Unspecialized version assumes that most types are not being used for base
Chris@16 721 // class chaining. We specialize for the operator templates defined in this
Chris@16 722 // library.
Chris@16 723 template<class T> struct is_chained_base {
Chris@16 724 typedef ::boost::detail::false_t value;
Chris@16 725 };
Chris@16 726
Chris@16 727 } // namespace boost
Chris@16 728
Chris@16 729 // Import a 4-type-argument operator template into boost (if necessary) and
Chris@16 730 // provide a specialization of 'is_chained_base<>' for it.
Chris@16 731 # define BOOST_OPERATOR_TEMPLATE4(template_name4) \
Chris@16 732 BOOST_IMPORT_TEMPLATE4(template_name4) \
Chris@16 733 template<class T, class U, class V, class W, class B> \
Chris@16 734 struct is_chained_base< ::boost::template_name4<T, U, V, W, B> > { \
Chris@16 735 typedef ::boost::detail::true_t value; \
Chris@16 736 };
Chris@16 737
Chris@16 738 // Import a 3-type-argument operator template into boost (if necessary) and
Chris@16 739 // provide a specialization of 'is_chained_base<>' for it.
Chris@16 740 # define BOOST_OPERATOR_TEMPLATE3(template_name3) \
Chris@16 741 BOOST_IMPORT_TEMPLATE3(template_name3) \
Chris@16 742 template<class T, class U, class V, class B> \
Chris@16 743 struct is_chained_base< ::boost::template_name3<T, U, V, B> > { \
Chris@16 744 typedef ::boost::detail::true_t value; \
Chris@16 745 };
Chris@16 746
Chris@16 747 // Import a 2-type-argument operator template into boost (if necessary) and
Chris@16 748 // provide a specialization of 'is_chained_base<>' for it.
Chris@16 749 # define BOOST_OPERATOR_TEMPLATE2(template_name2) \
Chris@16 750 BOOST_IMPORT_TEMPLATE2(template_name2) \
Chris@16 751 template<class T, class U, class B> \
Chris@16 752 struct is_chained_base< ::boost::template_name2<T, U, B> > { \
Chris@16 753 typedef ::boost::detail::true_t value; \
Chris@16 754 };
Chris@16 755
Chris@16 756 // Import a 1-type-argument operator template into boost (if necessary) and
Chris@16 757 // provide a specialization of 'is_chained_base<>' for it.
Chris@16 758 # define BOOST_OPERATOR_TEMPLATE1(template_name1) \
Chris@16 759 BOOST_IMPORT_TEMPLATE1(template_name1) \
Chris@16 760 template<class T, class B> \
Chris@16 761 struct is_chained_base< ::boost::template_name1<T, B> > { \
Chris@16 762 typedef ::boost::detail::true_t value; \
Chris@16 763 };
Chris@16 764
Chris@16 765 // BOOST_OPERATOR_TEMPLATE(template_name) defines template_name<> such that it
Chris@16 766 // can be used for specifying both 1-argument and 2-argument forms. Requires the
Chris@16 767 // existence of two previously defined class templates named '<template_name>1'
Chris@16 768 // and '<template_name>2' which must implement the corresponding 1- and 2-
Chris@16 769 // argument forms.
Chris@16 770 //
Chris@16 771 // The template type parameter O == is_chained_base<U>::value is used to
Chris@16 772 // distinguish whether the 2nd argument to <template_name> is being used for
Chris@16 773 // base class chaining from another boost operator template or is describing a
Chris@16 774 // 2nd operand type. O == true_t only when U is actually an another operator
Chris@16 775 // template from the library. Partial specialization is used to select an
Chris@16 776 // implementation in terms of either '<template_name>1' or '<template_name>2'.
Chris@16 777 //
Chris@16 778
Chris@16 779 # define BOOST_OPERATOR_TEMPLATE(template_name) \
Chris@16 780 template <class T \
Chris@16 781 ,class U = T \
Chris@16 782 ,class B = ::boost::detail::empty_base<T> \
Chris@16 783 ,class O = typename is_chained_base<U>::value \
Chris@16 784 > \
Chris@16 785 struct template_name : template_name##2<T, U, B> {}; \
Chris@16 786 \
Chris@16 787 template<class T, class U, class B> \
Chris@16 788 struct template_name<T, U, B, ::boost::detail::true_t> \
Chris@16 789 : template_name##1<T, U> {}; \
Chris@16 790 \
Chris@16 791 template <class T, class B> \
Chris@16 792 struct template_name<T, T, B, ::boost::detail::false_t> \
Chris@16 793 : template_name##1<T, B> {}; \
Chris@16 794 \
Chris@16 795 template<class T, class U, class B, class O> \
Chris@16 796 struct is_chained_base< ::boost::template_name<T, U, B, O> > { \
Chris@16 797 typedef ::boost::detail::true_t value; \
Chris@16 798 }; \
Chris@16 799 \
Chris@16 800 BOOST_OPERATOR_TEMPLATE2(template_name##2) \
Chris@16 801 BOOST_OPERATOR_TEMPLATE1(template_name##1)
Chris@16 802
Chris@16 803
Chris@16 804
Chris@16 805 namespace boost {
Chris@16 806
Chris@16 807 BOOST_OPERATOR_TEMPLATE(less_than_comparable)
Chris@16 808 BOOST_OPERATOR_TEMPLATE(equality_comparable)
Chris@16 809 BOOST_OPERATOR_TEMPLATE(multipliable)
Chris@16 810 BOOST_OPERATOR_TEMPLATE(addable)
Chris@16 811 BOOST_OPERATOR_TEMPLATE(subtractable)
Chris@16 812 BOOST_OPERATOR_TEMPLATE2(subtractable2_left)
Chris@16 813 BOOST_OPERATOR_TEMPLATE(dividable)
Chris@16 814 BOOST_OPERATOR_TEMPLATE2(dividable2_left)
Chris@16 815 BOOST_OPERATOR_TEMPLATE(modable)
Chris@16 816 BOOST_OPERATOR_TEMPLATE2(modable2_left)
Chris@16 817 BOOST_OPERATOR_TEMPLATE(xorable)
Chris@16 818 BOOST_OPERATOR_TEMPLATE(andable)
Chris@16 819 BOOST_OPERATOR_TEMPLATE(orable)
Chris@16 820
Chris@16 821 BOOST_OPERATOR_TEMPLATE1(incrementable)
Chris@16 822 BOOST_OPERATOR_TEMPLATE1(decrementable)
Chris@16 823
Chris@16 824 BOOST_OPERATOR_TEMPLATE2(dereferenceable)
Chris@16 825 BOOST_OPERATOR_TEMPLATE3(indexable)
Chris@16 826
Chris@16 827 BOOST_OPERATOR_TEMPLATE(left_shiftable)
Chris@16 828 BOOST_OPERATOR_TEMPLATE(right_shiftable)
Chris@16 829 BOOST_OPERATOR_TEMPLATE(equivalent)
Chris@16 830 BOOST_OPERATOR_TEMPLATE(partially_ordered)
Chris@16 831
Chris@16 832 BOOST_OPERATOR_TEMPLATE(totally_ordered)
Chris@16 833 BOOST_OPERATOR_TEMPLATE(additive)
Chris@16 834 BOOST_OPERATOR_TEMPLATE(multiplicative)
Chris@16 835 BOOST_OPERATOR_TEMPLATE(integer_multiplicative)
Chris@16 836 BOOST_OPERATOR_TEMPLATE(arithmetic)
Chris@16 837 BOOST_OPERATOR_TEMPLATE(integer_arithmetic)
Chris@16 838 BOOST_OPERATOR_TEMPLATE(bitwise)
Chris@16 839 BOOST_OPERATOR_TEMPLATE1(unit_steppable)
Chris@16 840 BOOST_OPERATOR_TEMPLATE(shiftable)
Chris@16 841 BOOST_OPERATOR_TEMPLATE(ring_operators)
Chris@16 842 BOOST_OPERATOR_TEMPLATE(ordered_ring_operators)
Chris@16 843 BOOST_OPERATOR_TEMPLATE(field_operators)
Chris@16 844 BOOST_OPERATOR_TEMPLATE(ordered_field_operators)
Chris@16 845 BOOST_OPERATOR_TEMPLATE(euclidian_ring_operators)
Chris@16 846 BOOST_OPERATOR_TEMPLATE(ordered_euclidian_ring_operators)
Chris@16 847 BOOST_OPERATOR_TEMPLATE(euclidean_ring_operators)
Chris@16 848 BOOST_OPERATOR_TEMPLATE(ordered_euclidean_ring_operators)
Chris@16 849 BOOST_OPERATOR_TEMPLATE2(input_iteratable)
Chris@16 850 BOOST_OPERATOR_TEMPLATE1(output_iteratable)
Chris@16 851 BOOST_OPERATOR_TEMPLATE2(forward_iteratable)
Chris@16 852 BOOST_OPERATOR_TEMPLATE2(bidirectional_iteratable)
Chris@16 853 BOOST_OPERATOR_TEMPLATE4(random_access_iteratable)
Chris@16 854
Chris@16 855 #undef BOOST_OPERATOR_TEMPLATE
Chris@16 856 #undef BOOST_OPERATOR_TEMPLATE4
Chris@16 857 #undef BOOST_OPERATOR_TEMPLATE3
Chris@16 858 #undef BOOST_OPERATOR_TEMPLATE2
Chris@16 859 #undef BOOST_OPERATOR_TEMPLATE1
Chris@16 860 #undef BOOST_IMPORT_TEMPLATE1
Chris@16 861 #undef BOOST_IMPORT_TEMPLATE2
Chris@16 862 #undef BOOST_IMPORT_TEMPLATE3
Chris@16 863 #undef BOOST_IMPORT_TEMPLATE4
Chris@16 864
Chris@16 865 // The following 'operators' classes can only be used portably if the derived class
Chris@16 866 // declares ALL of the required member operators.
Chris@16 867 template <class T, class U>
Chris@16 868 struct operators2
Chris@16 869 : totally_ordered2<T,U
Chris@16 870 , integer_arithmetic2<T,U
Chris@16 871 , bitwise2<T,U
Chris@16 872 > > > {};
Chris@16 873
Chris@16 874 template <class T, class U = T>
Chris@16 875 struct operators : operators2<T, U> {};
Chris@16 876
Chris@16 877 template <class T> struct operators<T, T>
Chris@16 878 : totally_ordered<T
Chris@16 879 , integer_arithmetic<T
Chris@16 880 , bitwise<T
Chris@16 881 , unit_steppable<T
Chris@16 882 > > > > {};
Chris@16 883
Chris@16 884 // Iterator helper classes (contributed by Jeremy Siek) -------------------//
Chris@16 885 // (Input and output iterator helpers contributed by Daryle Walker) -------//
Chris@16 886 // (Changed to use combined operator classes by Daryle Walker) ------------//
Chris@16 887 template <class T,
Chris@16 888 class V,
Chris@16 889 class D = std::ptrdiff_t,
Chris@16 890 class P = V const *,
Chris@16 891 class R = V const &>
Chris@16 892 struct input_iterator_helper
Chris@16 893 : input_iteratable<T, P
Chris@16 894 , boost::iterator<std::input_iterator_tag, V, D, P, R
Chris@16 895 > > {};
Chris@16 896
Chris@16 897 template<class T>
Chris@16 898 struct output_iterator_helper
Chris@16 899 : output_iteratable<T
Chris@16 900 , boost::iterator<std::output_iterator_tag, void, void, void, void
Chris@16 901 > >
Chris@16 902 {
Chris@16 903 T& operator*() { return static_cast<T&>(*this); }
Chris@16 904 T& operator++() { return static_cast<T&>(*this); }
Chris@16 905 };
Chris@16 906
Chris@16 907 template <class T,
Chris@16 908 class V,
Chris@16 909 class D = std::ptrdiff_t,
Chris@16 910 class P = V*,
Chris@16 911 class R = V&>
Chris@16 912 struct forward_iterator_helper
Chris@16 913 : forward_iteratable<T, P
Chris@16 914 , boost::iterator<std::forward_iterator_tag, V, D, P, R
Chris@16 915 > > {};
Chris@16 916
Chris@16 917 template <class T,
Chris@16 918 class V,
Chris@16 919 class D = std::ptrdiff_t,
Chris@16 920 class P = V*,
Chris@16 921 class R = V&>
Chris@16 922 struct bidirectional_iterator_helper
Chris@16 923 : bidirectional_iteratable<T, P
Chris@16 924 , boost::iterator<std::bidirectional_iterator_tag, V, D, P, R
Chris@16 925 > > {};
Chris@16 926
Chris@16 927 template <class T,
Chris@16 928 class V,
Chris@16 929 class D = std::ptrdiff_t,
Chris@16 930 class P = V*,
Chris@16 931 class R = V&>
Chris@16 932 struct random_access_iterator_helper
Chris@16 933 : random_access_iteratable<T, P, D, R
Chris@16 934 , boost::iterator<std::random_access_iterator_tag, V, D, P, R
Chris@16 935 > >
Chris@16 936 {
Chris@16 937 friend D requires_difference_operator(const T& x, const T& y) {
Chris@16 938 return x - y;
Chris@16 939 }
Chris@16 940 }; // random_access_iterator_helper
Chris@16 941
Chris@16 942 } // namespace boost
Chris@16 943
Chris@16 944 #if defined(__sgi) && !defined(__GNUC__)
Chris@16 945 #pragma reset woff 1234
Chris@16 946 #endif
Chris@16 947
Chris@16 948 #endif // BOOST_OPERATORS_HPP