Compare commits

...

72 Commits

Author SHA1 Message Date
nobody
cfb38f7097 This commit was manufactured by cvs2svn to create branch
'python-v2-dev'.

[SVN r14785]
2002-08-12 13:35:54 +00:00
Beman Dawes
4ba6a96822 fix test_main signature
[SVN r14783]
2002-08-12 13:22:40 +00:00
John Maddock
1ea4140d56 Added tests for BOOST_NO_STD_ITERATOR_TRAITS
[SVN r14654]
2002-07-31 11:25:25 +00:00
Douglas Gregor
351d4ecb15 Document policies() member of iterator_adaptor
[SVN r14613]
2002-07-26 00:03:24 +00:00
Beman Dawes
7fbf84dcc6 BaseType -> Base in one more place
[SVN r14605]
2002-07-25 19:10:05 +00:00
Dave Abrahams
3ff49b272d fixup
[SVN r14598]
2002-07-25 14:16:54 +00:00
Dave Abrahams
5b52e3d418 Fix doc based on Beman's feedback
[SVN r14596]
2002-07-25 13:52:48 +00:00
Dave Abrahams
8c0eb498d3 Fix unversioned VC++ checks
[SVN r14436]
2002-07-13 12:26:19 +00:00
Dave Abrahams
48a81ef7ea VC++ fixes
[SVN r14435]
2002-07-13 12:22:51 +00:00
Dave Abrahams
f7610c9b26 fix link
[SVN r14318]
2002-07-05 23:51:20 +00:00
Dave Abrahams
1755eaf019 Merged from RC_1_28_0
[SVN r13944]
2002-05-16 00:56:42 +00:00
John Maddock
6b8b218efb Removed tabs, fixed end of files.
[SVN r13803]
2002-05-10 11:35:38 +00:00
Beman Dawes
333d79b345 Add index.html so automatic tools work correctly
[SVN r13725]
2002-05-07 19:23:05 +00:00
John Maddock
f0fa436fe4 Added new config macro BOOST_HAS_MS_INT64 to detect presence of __int64 data type.
Modified boost source to use BOOST_HAS_LONG_LONG and BOOST_HAS_MS_INT64
   where appropriate to do so.


[SVN r13714]
2002-05-07 11:24:29 +00:00
John Maddock
13e6d78fa8 Fixes for Borland C++ Builder 6
[SVN r13662]
2002-05-04 11:03:42 +00:00
John Maddock
7126ea2685 Borland C++ Builder 6 fixes
[SVN r13659]
2002-05-04 10:55:15 +00:00
John Maddock
a37518cb4a Fixed broken links.
[SVN r13574]
2002-04-27 11:05:49 +00:00
Jens Maurer
64b3e8c3bd add missing #include <iterator>
[SVN r13554]
2002-04-23 19:52:11 +00:00
Peter Dimov
339937380e MSVC fixes.
[SVN r13476]
2002-04-13 13:19:57 +00:00
Dave Abrahams
6156f0d302 Roll addressof() patch back in!
[SVN r13433]
2002-04-10 17:01:35 +00:00
Douglas Gregor
00560e8e17 addressof.hpp:
- Peter Dimov suggested a fix to deal with those evil cv-qualifiers


[SVN r13431]
2002-04-10 14:47:32 +00:00
Dave Abrahams
029ff9828f Roll back addressof() patch temporarily
[SVN r13428]
2002-04-10 09:48:30 +00:00
Douglas Gregor
ec188c7c3e Make local classes nonlocal to silence annoying warnings from Borland C++
[SVN r13418]
2002-04-10 04:00:22 +00:00
Douglas Gregor
0a0296a5d0 ref.hpp:
- Use addressof() instead of & operator


[SVN r13416]
2002-04-10 03:36:17 +00:00
Douglas Gregor
6e26a5bbe7 boost/utility.hpp:
- Include boost/utility/addressof.hpp

boost/utility/addressof.hpp:
  - addressof() implementation

libs/utility/utility.htm:
  - Document addressof

libs/utility/addressof_test.cpp:
  - Test addressof()


[SVN r13414]
2002-04-10 03:31:18 +00:00
Douglas Gregor
dc1b6246a0 boost/ref.hpp:
- Added get_pointer method to return a pointer (instead of a reference)

libs/bind/ref.html:
  - Document get_pointer


[SVN r13322]
2002-03-31 00:24:00 +00:00
John Maddock
15f69eaf14 Fixed new problem with Borland compile -
code clashes with some new type traits workarounds for some reason.


[SVN r13226]
2002-03-19 11:33:00 +00:00
Dave Abrahams
4774a0d325 Added Copyright
[SVN r13145]
2002-03-09 20:34:06 +00:00
Jens Maurer
be78ab72c9 update expected failures for Sun CC
[SVN r13101]
2002-03-05 20:41:37 +00:00
Dave Abrahams
0bc4a1b20d Warning suppressioni from Craig Rodrigues
[SVN r13098]
2002-03-05 18:55:49 +00:00
Darin Adler
c8b674d105 Add missing paren.
[SVN r12997]
2002-03-01 17:43:00 +00:00
John Maddock
b421d4725a Fixed expected failures for gcc 3.1
[SVN r12994]
2002-03-01 12:27:01 +00:00
Dave Abrahams
1662bb5713 use of "small" changed to "small_" to suppress confusion on some compilers
[SVN r12916]
2002-02-24 02:35:19 +00:00
Toon Knapen
ad79a21abd added portability note about using std::vector's as Base with VC++
[SVN r12875]
2002-02-21 12:09:46 +00:00
Peter Dimov
19645a52e6 Added a default constructor to shared_count and shared_ptr for incomplete types (void).
[SVN r12815]
2002-02-15 13:31:58 +00:00
John Maddock
74c3077c9a Added test cases for incomplete and abstract base class types.
[SVN r12803]
2002-02-14 12:57:32 +00:00
John Maddock
1f29191329 Modified call_traits to work with incomplete types.
[SVN r12800]
2002-02-14 12:54:57 +00:00
Darin Adler
4b636a7680 Always say "private noncopyable" to avoid warnings.
[SVN r12762]
2002-02-08 20:08:15 +00:00
Jeremy Siek
e6fc2555f3 removed tabs
[SVN r12707]
2002-02-04 20:29:35 +00:00
Darin Adler
e27d0fcf2a New smart pointer documentation. Related clean-up of the smart pointer
library. Changing includes to include the new individual smart pointer
headers. Replacing old smart pointer library with an include of the new
smart pointer headers. Simplify ifdefs that involve the member templates
macros now that BOOST_MSVC6_MEMBER_TEMPLATES is also guaranteed to bet
set for platforms that have full member templates.


[SVN r12647]
2002-02-02 18:36:12 +00:00
Dave Abrahams
2643c33b20 Doc fixes from Thomas Witt
[SVN r12621]
2002-02-01 13:03:21 +00:00
Aleksey Gurtovoy
71af1e77c8 compile-time ref.hpp header test, initial checkin
[SVN r12525]
2002-01-27 13:39:06 +00:00
Aleksey Gurtovoy
99e7406bd9 ref_ct_test.cpp
[SVN r12524]
2002-01-27 13:32:37 +00:00
Aleksey Gurtovoy
413265f497 compile-time ref.hpp header test, initial checkin
[SVN r12522]
2002-01-27 13:07:20 +00:00
Aleksey Gurtovoy
fe44cdf09b made 'reference_wrapper' Assignable
[SVN r12520]
2002-01-27 13:02:27 +00:00
Peter Dimov
e413428d71 Added tests for the new smart pointers.
[SVN r12500]
2002-01-25 13:54:30 +00:00
Darin Adler
88b9822db7 Mark inline to avoid warning with "require prototypes" on.
[SVN r12490]
2002-01-24 19:15:30 +00:00
Peter Dimov
24045c0cd7 #included <boost/checked_delete.hpp>, removed unnecessary #includes.
[SVN r12488]
2002-01-24 17:47:08 +00:00
Dave Abrahams
d2aa9f4a84 added missing #include of boost/config.hpp
[SVN r12483]
2002-01-24 16:55:41 +00:00
Dave Abrahams
d2a5fd169f initial checkin
[SVN r12481]
2002-01-24 16:52:06 +00:00
Peter Dimov
4e350d9934 Modified is_reference_wrapper<> to work for reference types.
[SVN r12475]
2002-01-24 13:28:08 +00:00
Dave Abrahams
f3f697bbc8 added is_reference_wrapper<>, unwrap_reference<>
[SVN r12470]
2002-01-23 21:19:14 +00:00
Darin Adler
c7c09696db Tweak comments. Include <assert.h> and <boost/current_function.hpp> only
when needed.


[SVN r12446]
2002-01-22 18:28:33 +00:00
Peter Dimov
dbcc58d984 Smart pointer enhancements, initial commit
[SVN r12439]
2002-01-22 13:38:52 +00:00
Dave Abrahams
8231310c4d initial checkin
[SVN r12390]
2002-01-21 01:29:06 +00:00
Beman Dawes
2988140430 tabs
[SVN r12360]
2002-01-19 16:07:28 +00:00
John Maddock
7387966005 Stripped tabs from source
[SVN r12351]
2002-01-19 12:38:14 +00:00
Jeremy Siek
e0a5a61375 removed eroneous "detail::" prefix
[SVN r12326]
2002-01-15 19:14:53 +00:00
Jeremy Siek
66ecd70689 removed std:: prefix from slist
[SVN r12310]
2002-01-14 14:57:20 +00:00
Dave Abrahams
67f4f45653 Fixed violation of 'explicit' constructor
[SVN r12256]
2002-01-09 13:15:54 +00:00
Dave Abrahams
1bf28b3de2 Fixes for Borland
[SVN r12254]
2002-01-09 12:11:37 +00:00
John Maddock
eb3c3435d7 Updated expected results
[SVN r12250]
2002-01-08 13:01:15 +00:00
Dave Abrahams
8a81d8b16c Workarounds for MSVC
[SVN r12246]
2002-01-07 19:24:45 +00:00
Toon Knapen
bc9d8b13d0 converted some of the old terminology (OrderIterator) to the current
terminology (IndexIterator)


[SVN r12164]
2001-12-28 15:49:45 +00:00
Dave Abrahams
4768b167ab Removed obsolete mentions of "less"; Added formalized Policies Concept description
[SVN r12056]
2001-12-14 12:54:21 +00:00
Dave Abrahams
591ff70ed1 many fixes
[SVN r12054]
2001-12-13 19:43:35 +00:00
Dave Abrahams
7bf2ad0b22 VC6 patch
[SVN r12045]
2001-12-13 18:24:29 +00:00
Jens Maurer
409c79b2e4 fix example (thanks to Michael Stevens)
[SVN r11979]
2001-12-08 08:39:27 +00:00
Toon Knapen
d0410691a1 removed calls to non-standard std::iota (SGI extension)
[SVN r11904]
2001-12-04 08:02:36 +00:00
Dave Abrahams
64e5115138 Fixed spelling error ing gcc-3.0 bug workaround
[SVN r11888]
2001-12-03 21:48:54 +00:00
Dave Abrahams
7ae912d83c Rolled in Helmut's fixes for random_access_iterable; rolled back
workarounds for that problem.


[SVN r11887]
2001-12-03 21:47:58 +00:00
Toon Knapen
2937f5876c changed std::iota call (SGI extension) to a manual loop
in permutation_iterator test


[SVN r11869]
2001-12-03 08:35:08 +00:00
43 changed files with 1363 additions and 272 deletions

46
addressof_test.cpp Normal file
View File

@@ -0,0 +1,46 @@
// Copyright (C) 2002 Brad King (brad.king@kitware.com)
// Doug Gregor (gregod@cs.rpi.edu)
//
// Permission to copy, use, sell and distribute this software is granted
// provided this copyright notice appears in all copies.
// Permission to modify the code and to distribute modified code is granted
// provided this copyright notice appears in all copies, and a notice
// that the code was modified is included with the copyright notice.
//
// This software is provided "as is" without express or implied warranty,
// and with no claim as to its suitability for any purpose.
// For more information, see http://www.boost.org
#define BOOST_INCLUDE_MAIN
#include <boost/test/test_tools.hpp>
#include <boost/utility.hpp>
struct useless_type {};
class nonaddressable {
public:
void dummy(); // Silence GCC warning: all member of class are private
private:
useless_type operator&() const;
};
int test_main(int, char*[])
{
nonaddressable* px = new nonaddressable();
nonaddressable& x = *px;
BOOST_TEST(boost::addressof(x) == px);
const nonaddressable& cx = *px;
BOOST_TEST(boost::addressof(cx) == static_cast<const nonaddressable*>(px));
volatile nonaddressable& vx = *px;
BOOST_TEST(boost::addressof(vx) == static_cast<volatile nonaddressable*>(px));
const volatile nonaddressable& cvx = *px;
BOOST_TEST(boost::addressof(cvx) == static_cast<const volatile nonaddressable*>(px));
return 0;
}

33
assert_test.cpp Normal file
View File

@@ -0,0 +1,33 @@
#if defined(_MSC_VER) && !defined(__ICL)
#pragma warning(disable: 4786) // identifier truncated in debug info
#pragma warning(disable: 4710) // function not inlined
#pragma warning(disable: 4711) // function selected for automatic inline expansion
#pragma warning(disable: 4514) // unreferenced inline removed
#endif
//
// assert_test.cpp - a test for boost/assert.hpp
//
// Copyright (c) 2002 Peter Dimov and Multi Media Ltd.
//
// Permission to copy, use, modify, sell and distribute this software
// is granted provided this copyright notice appears in all copies.
// This software is provided "as is" without express or implied
// warranty, and with no claim as to its suitability for any purpose.
//
#define BOOST_DEBUG 1
#include <boost/assert.hpp>
#include <cstdio>
bool boost_error(char const * expr, char const * func, char const * file, long line)
{
std::printf("%s(%ld): Assertion '%s' failed in function '%s'\n", file, line, expr, func);
return true; // fail w/ standard assert()
}
int main()
{
BOOST_ASSERT(0 == 1);
}

View File

@@ -57,7 +57,7 @@ struct object_id_compare
// A singleton of this type coordinates the acknowledgements // A singleton of this type coordinates the acknowledgements
// of objects being created and used. // of objects being created and used.
class object_registrar class object_registrar
: boost::noncopyable : private boost::noncopyable
{ {
public: public:

249
binary_search_test.cpp Normal file
View File

@@ -0,0 +1,249 @@
// (C) Copyright David Abrahams 2000. Permission to copy, use, modify,
// sell and distribute this software is granted provided this
// copyright notice appears in all copies. This software is provided
// "as is" without express or implied warranty, and with no claim as
// to its suitability for any purpose.
#include <vector>
#include <string>
#include <memory>
#include <climits>
#include <iostream>
#include <cassert>
#include <stdlib.h> // for rand(). Would use cstdlib but VC6.4 doesn't put it in std::
#include <list>
#include <algorithm>
#include <boost/detail/binary_search.hpp>
#if defined(__SGI_STL_PORT) ? defined(__SGI_STL_OWN_IOSTREAMS) : (!defined(__GNUC__) || __GNUC__ > 2)
# define USE_SSTREAM
#endif
#ifdef USE_SSTREAM
# include <sstream>
#else
# include <strstream>
#endif
namespace {
typedef std::vector<std::string> string_vector;
const std::size_t sequence_length = 1000;
unsigned random_number()
{
return static_cast<unsigned>(::rand()) % sequence_length;
}
# ifndef USE_SSTREAM
class unfreezer {
public:
unfreezer(std::ostrstream& s) : m_stream(s) {}
~unfreezer() { m_stream.freeze(false); }
private:
std::ostrstream& m_stream;
};
# endif
template <class T>
void push_back_random_number_string(T& seq)
{
unsigned value = random_number();
# if defined(__SGI_STL_PORT) ? defined(__SGI_STL_OWN_IOSTREAMS) : (!defined(__GNUC__) || __GNUC__ > 2)
std::ostringstream s;
s << value;
seq.push_back(s.str());
# else
std::ostrstream s;
auto unfreezer unfreeze(s);
s << value << char(0);
seq.push_back(std::string(s.str()));
# endif
}
inline unsigned to_int(unsigned x) { return x; }
inline unsigned to_int(const std::string& x) { return atoi(x.c_str()); }
struct cmp
{
template <class A1, class A2>
inline bool operator()(const A1& a1, const A2& a2) const
{
return to_int(a1) < to_int(a2);
}
};
inline bool operator<(const std::string& x, const unsigned y)
{
return to_int(x) < y;
}
inline bool operator<(const unsigned y, const std::string& x)
{
return y < to_int(x);
}
template <class T> void sort_by_value(T&);
template <>
void sort_by_value(std::vector<std::string>& v)
{
std::sort(v.begin(), v.end(), cmp());
}
template <class T>
void random_sorted_sequence(T& seq)
{
seq.clear();
for (std::size_t i = 0; i < sequence_length; ++i)
{
push_back_random_number_string(seq);
}
sort_by_value(seq);
}
# if defined(BOOST_MSVC) && BOOST_MSVC < 1300 && !defined(__SGI_STL_PORT)
// VC6's standard lib doesn't have a template member function for list::sort()
template <>
void random_sorted_sequence(std::list<std::string>& result)
{
std::vector<std::string> seq;
seq.reserve(sequence_length);
for (std::size_t i = 0; i < sequence_length; ++i)
{
push_back_random_number_string(seq);
}
sort_by_value(seq);
result.resize(seq.size());
std::copy(seq.begin(), seq.end(), result.begin());
}
#else
template <>
inline void sort_by_value(std::list<std::string>& l)
{
l.sort(cmp());
}
# endif
// A way to select the comparisons with/without a Compare parameter for testing.
template <class Compare> struct searches
{
template <class Iterator, class Key>
static Iterator lower_bound(Iterator start, Iterator finish, Key key, Compare cmp)
{ return boost::detail::lower_bound(start, finish, key, cmp); }
template <class Iterator, class Key>
static Iterator upper_bound(Iterator start, Iterator finish, Key key, Compare cmp)
{ return boost::detail::upper_bound(start, finish, key, cmp); }
template <class Iterator, class Key>
static std::pair<Iterator, Iterator> equal_range(Iterator start, Iterator finish, Key key, Compare cmp)
{ return boost::detail::equal_range(start, finish, key, cmp); }
template <class Iterator, class Key>
static bool binary_search(Iterator start, Iterator finish, Key key, Compare cmp)
{ return boost::detail::binary_search(start, finish, key, cmp); }
};
struct no_compare {};
template <> struct searches<no_compare>
{
template <class Iterator, class Key>
static Iterator lower_bound(Iterator start, Iterator finish, Key key, no_compare)
{ return boost::detail::lower_bound(start, finish, key); }
template <class Iterator, class Key>
static Iterator upper_bound(Iterator start, Iterator finish, Key key, no_compare)
{ return boost::detail::upper_bound(start, finish, key); }
template <class Iterator, class Key>
static std::pair<Iterator, Iterator> equal_range(Iterator start, Iterator finish, Key key, no_compare)
{ return boost::detail::equal_range(start, finish, key); }
template <class Iterator, class Key>
static bool binary_search(Iterator start, Iterator finish, Key key, no_compare)
{ return boost::detail::binary_search(start, finish, key); }
};
template <class Sequence, class Compare>
void test_loop(Sequence& x, Compare cmp, unsigned long test_count)
{
typedef typename Sequence::const_iterator const_iterator;
for (unsigned long i = 0; i < test_count; ++i)
{
random_sorted_sequence(x);
const const_iterator start = x.begin();
const const_iterator finish = x.end();
unsigned key = random_number();
const const_iterator l = searches<Compare>::lower_bound(start, finish, key, cmp);
const const_iterator u = searches<Compare>::upper_bound(start, finish, key, cmp);
bool found_l = false;
bool found_u = false;
std::size_t index = 0;
std::size_t count = 0;
unsigned last_value = 0;
for (const_iterator p = start; p != finish; ++p)
{
if (p == l)
found_l = true;
if (p == u)
{
assert(found_l);
found_u = true;
}
unsigned value = to_int(*p);
assert(value >= last_value);
last_value = value;
if (!found_l)
{
++index;
assert(to_int(*p) < key);
}
else if (!found_u)
{
++count;
assert(to_int(*p) == key);
}
else
assert(to_int(*p) > key);
}
assert(found_l || l == finish);
assert(found_u || u == finish);
std::pair<const_iterator, const_iterator>
range = searches<Compare>::equal_range(start, finish, key, cmp);
assert(range.first == l);
assert(range.second == u);
bool found = searches<Compare>::binary_search(start, finish, key, cmp);
assert(found == (u != l));
std::cout << "found " << count << " copies of " << key << " at index " << index << "\n";
}
}
}
int main()
{
std::vector<std::string> x;
std::cout << "=== testing random-access iterators with <: ===\n";
test_loop(x, no_compare(), 25);
std::cout << "=== testing random-access iterators with compare: ===\n";
test_loop(x, cmp(), 25);
std::list<std::string> y;
std::cout << "=== testing bidirectional iterators with <: ===\n";
test_loop(y, no_compare(), 25);
std::cout << "=== testing bidirectional iterators with compare: ===\n";
test_loop(y, cmp(), 25);
std::cerr << "******TEST PASSED******\n";
return 0;
}

View File

@@ -5,7 +5,7 @@
content="text/html; charset=iso-8859-1"> content="text/html; charset=iso-8859-1">
<meta name="Template" <meta name="Template"
content="C:\PROGRAM FILES\MICROSOFT OFFICE\OFFICE\html.dot"> content="C:\PROGRAM FILES\MICROSOFT OFFICE\OFFICE\html.dot">
<meta name="GENERATOR" content="Microsoft FrontPage 4.0"> <meta name="GENERATOR" content="Microsoft FrontPage Express 2.0">
<title>Call Traits</title> <title>Call Traits</title>
</head> </head>
@@ -592,7 +592,8 @@ would prevent template argument deduction from functioning.</p>
<p>The call_traits template will &quot;optimize&quot; the passing <p>The call_traits template will &quot;optimize&quot; the passing
of a small built-in type as a function parameter, this mainly has of a small built-in type as a function parameter, this mainly has
an effect when the parameter is used within a loop body. In the an effect when the parameter is used within a loop body. In the
following example (see <a href="algo_opt_examples.cpp">algo_opt_examples.cpp</a>), following example (see <a
href="../type_traits/examples/fill_example.cpp">fill_example.cpp</a>),
a version of std::fill is optimized in two ways: if the type a version of std::fill is optimized in two ways: if the type
passed is a single byte built-in type then std::memset is used to passed is a single byte built-in type then std::memset is used to
effect the fill, otherwise a conventional C++ implemention is effect the fill, otherwise a conventional C++ implemention is
@@ -751,7 +752,8 @@ Hinnant and John Maddock.</p>
<p>Maintained by <a href="mailto:John_Maddock@compuserve.com">John <p>Maintained by <a href="mailto:John_Maddock@compuserve.com">John
Maddock</a>, the latest version of this file can be found at <a Maddock</a>, the latest version of this file can be found at <a
href="http://www.boost.org/">www.boost.org</a>, and the boost href="http://www.boost.org/">www.boost.org</a>, and the boost
discussion list at <a href="http://www.yahoogroups.com/list/boost">www.yahoogroups.com/list/boost</a>.</p> discussion list at <a
href="http://www.yahoogroups.com/list/boost">www.yahoogroups.com/list/boost</a>.</p>
<p>.</p> <p>.</p>

View File

@@ -6,6 +6,8 @@
// warranty, and with no claim as to its suitability for any purpose. // warranty, and with no claim as to its suitability for any purpose.
// standalone test program for <boost/call_traits.hpp> // standalone test program for <boost/call_traits.hpp>
// 18 Mar 2002:
// Changed some names to prevent conflicts with some new type_traits additions.
// 03 Oct 2000: // 03 Oct 2000:
// Enabled extra tests for VC6. // Enabled extra tests for VC6.
@@ -78,7 +80,7 @@ struct contained<T[N]>
#endif #endif
template <class T> template <class T>
contained<typename boost::call_traits<T>::value_type> wrap(const T& t) contained<typename boost::call_traits<T>::value_type> test_wrap_type(const T& t)
{ {
typedef typename boost::call_traits<T>::value_type ct; typedef typename boost::call_traits<T>::value_type ct;
return contained<ct>(t); return contained<ct>(t);
@@ -204,7 +206,7 @@ int main(int argc, char *argv[ ])
c2(i); c2(i);
int* pi = &i; int* pi = &i;
int a[2] = {1,2}; int a[2] = {1,2};
#if (defined(BOOST_MSVC6_MEMBER_TEMPLATES) || !defined(BOOST_NO_MEMBER_TEMPLATES)) && !defined(__ICL) #if defined(BOOST_MSVC6_MEMBER_TEMPLATES) && !defined(__ICL)
call_traits_checker<int*> c3; call_traits_checker<int*> c3;
c3(pi); c3(pi);
call_traits_checker<int&> c4; call_traits_checker<int&> c4;
@@ -217,9 +219,9 @@ int main(int argc, char *argv[ ])
#endif #endif
#endif #endif
check_wrap(wrap(2), 2); check_wrap(test_wrap_type(2), 2);
#if !defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION) && !defined(__SUNPRO_CC) #if !defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION) && !defined(__SUNPRO_CC)
check_wrap(wrap(a), a); check_wrap(test_wrap_type(a), a);
check_make_pair(test::make_pair(a, a), a, a); check_make_pair(test::make_pair(a, a), a, a);
#endif #endif
@@ -240,12 +242,12 @@ int main(int argc, char *argv[ ])
type_test(int*&, boost::call_traits<int*>::reference) type_test(int*&, boost::call_traits<int*>::reference)
type_test(int*const&, boost::call_traits<int*>::const_reference) type_test(int*const&, boost::call_traits<int*>::const_reference)
type_test(int*const, boost::call_traits<int*>::param_type) type_test(int*const, boost::call_traits<int*>::param_type)
#if defined(BOOST_MSVC6_MEMBER_TEMPLATES) || !defined(BOOST_NO_MEMBER_TEMPLATES) #if defined(BOOST_MSVC6_MEMBER_TEMPLATES)
type_test(int&, boost::call_traits<int&>::value_type) type_test(int&, boost::call_traits<int&>::value_type)
type_test(int&, boost::call_traits<int&>::reference) type_test(int&, boost::call_traits<int&>::reference)
type_test(const int&, boost::call_traits<int&>::const_reference) type_test(const int&, boost::call_traits<int&>::const_reference)
type_test(int&, boost::call_traits<int&>::param_type) type_test(int&, boost::call_traits<int&>::param_type)
#if !(defined(__GNUC__) && (__GNUC__ < 4)) #if !(defined(__GNUC__) && ((__GNUC__ < 3) || (__GNUC__ == 3) && (__GNUC_MINOR__ < 1)))
type_test(int&, boost::call_traits<cr_type>::value_type) type_test(int&, boost::call_traits<cr_type>::value_type)
type_test(int&, boost::call_traits<cr_type>::reference) type_test(int&, boost::call_traits<cr_type>::reference)
type_test(const int&, boost::call_traits<cr_type>::const_reference) type_test(const int&, boost::call_traits<cr_type>::const_reference)
@@ -268,16 +270,26 @@ int main(int argc, char *argv[ ])
type_test(const int(&)[3], boost::call_traits<const int[3]>::reference) type_test(const int(&)[3], boost::call_traits<const int[3]>::reference)
type_test(const int(&)[3], boost::call_traits<const int[3]>::const_reference) type_test(const int(&)[3], boost::call_traits<const int[3]>::const_reference)
type_test(const int*const, boost::call_traits<const int[3]>::param_type) type_test(const int*const, boost::call_traits<const int[3]>::param_type)
// test with abstract base class:
type_test(test_abc1, boost::call_traits<test_abc1>::value_type)
type_test(test_abc1&, boost::call_traits<test_abc1>::reference)
type_test(const test_abc1&, boost::call_traits<test_abc1>::const_reference)
type_test(const test_abc1&, boost::call_traits<test_abc1>::param_type)
#else #else
std::cout << "You're compiler does not support partial template instantiation, skipping 8 tests (8 errors)" << std::endl; std::cout << "You're compiler does not support partial template specialiation, skipping 8 tests (8 errors)" << std::endl;
failures += 8; failures += 12;
test_count += 8; test_count += 12;
#endif #endif
#else #else
std::cout << "You're compiler does not support partial template instantiation, skipping 20 tests (20 errors)" << std::endl; std::cout << "You're compiler does not support partial template specialiation, skipping 20 tests (20 errors)" << std::endl;
failures += 20; failures += 24;
test_count += 20; test_count += 24;
#endif #endif
// test with an incomplete type:
type_test(incomplete_type, boost::call_traits<incomplete_type>::value_type)
type_test(incomplete_type&, boost::call_traits<incomplete_type>::reference)
type_test(const incomplete_type&, boost::call_traits<incomplete_type>::const_reference)
type_test(const incomplete_type&, boost::call_traits<incomplete_type>::param_type)
return check_result(argc, argv); return check_result(argc, argv);
} }
@@ -388,7 +400,7 @@ void call_traits_test<T, true>::assert_construct(typename boost::call_traits<T>:
template struct call_traits_test<int>; template struct call_traits_test<int>;
template struct call_traits_test<const int>; template struct call_traits_test<const int>;
template struct call_traits_test<int*>; template struct call_traits_test<int*>;
#if defined(BOOST_MSVC6_MEMBER_TEMPLATES) || !defined(BOOST_NO_MEMBER_TEMPLATES) #if defined(BOOST_MSVC6_MEMBER_TEMPLATES)
template struct call_traits_test<int&>; template struct call_traits_test<int&>;
template struct call_traits_test<const int&>; template struct call_traits_test<const int&>;
#if !defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION) && !defined(__SUNPRO_CC) #if !defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION) && !defined(__SUNPRO_CC)
@@ -397,24 +409,22 @@ template struct call_traits_test<int[2], true>;
#endif #endif
#ifdef BOOST_MSVC #ifdef BOOST_MSVC
unsigned int expected_failures = 10; unsigned int expected_failures = 14;
#elif defined(__SUNPRO_CC) #elif defined(__SUNPRO_CC)
#if(__SUNPRO_CC <= 0x520) #if(__SUNPRO_CC <= 0x520)
unsigned int expected_failures = 14; unsigned int expected_failures = 18;
#elif(__SUNPRO_CC <= 0x530) #elif(__SUNPRO_CC < 0x530)
unsigned int expected_failures = 13; unsigned int expected_failures = 17;
#else #else
unsigned int expected_failures = 6; unsigned int expected_failures = 6;
#endif #endif
#elif defined(__BORLANDC__) #elif defined(__BORLANDC__)
unsigned int expected_failures = 2; unsigned int expected_failures = 2;
#elif defined(__GNUC__) #elif (defined(__GNUC__) && ((__GNUC__ < 3) || (__GNUC__ == 3) && (__GNUC_MINOR__ < 1)))
unsigned int expected_failures = 4; unsigned int expected_failures = 4;
#elif defined(__HP_aCC)
unsigned int expected_failures = 24;
#else #else
unsigned int expected_failures = 0; unsigned int expected_failures = 0;
#endif #endif

View File

@@ -329,7 +329,7 @@ void compressed_pair_array_tester<T1, T2>::test(first_param_type p1, second_para
BOOST_TEST(sizeof(T2) == sizeof(cp1.second())); BOOST_TEST(sizeof(T2) == sizeof(cp1.second()));
} }
int test_main(int, char **) int test_main(int, char *[])
{ {
// declare some variables to pass to the tester: // declare some variables to pass to the tester:
non_empty1 ne1(2); non_empty1 ne1(2);

View File

@@ -36,13 +36,16 @@ int main(int, char*[])
std::vector<std::vector<int>::iterator> pointers; std::vector<std::vector<int>::iterator> pointers;
// Use counting iterator to fill in the array of pointers. // Use counting iterator to fill in the array of pointers.
// causes an ICE with MSVC6
#if !defined(BOOST_MSVC) || (BOOST_MSVC > 1200)
std::copy(boost::make_counting_iterator(numbers.begin()), std::copy(boost::make_counting_iterator(numbers.begin()),
boost::make_counting_iterator(numbers.end()), boost::make_counting_iterator(numbers.end()),
std::back_inserter(pointers)); std::back_inserter(pointers));
#endif
#if !defined(BOOST_MSVC) || (BOOST_MSVC > 1300)
// Use indirect iterator to print out numbers by accessing // Use indirect iterator to print out numbers by accessing
// them through the array of pointers. // them through the array of pointers.
#ifndef BOOST_MSVC
std::cout << "indirectly printing out the numbers from 0 to " std::cout << "indirectly printing out the numbers from 0 to "
<< N << std::endl; << N << std::endl;
std::copy(boost::make_indirect_iterator(pointers.begin()), std::copy(boost::make_indirect_iterator(pointers.begin()),

View File

@@ -27,7 +27,9 @@
#include <climits> #include <climits>
#include <iterator> #include <iterator>
#include <stdlib.h> #include <stdlib.h>
#include <boost/tuple/tuple.hpp> #ifndef __BORLANDC__
# include <boost/tuple/tuple.hpp>
#endif
#include <vector> #include <vector>
#include <list> #include <list>
#include <cassert> #include <cassert>
@@ -72,8 +74,12 @@ void category_test(
// Try some binary searches on the range to show that it's ordered // Try some binary searches on the range to show that it's ordered
assert(std::binary_search(start, finish, *internal)); assert(std::binary_search(start, finish, *internal));
CountingIterator x,y;
boost::tie(x,y) = std::equal_range(start, finish, *internal); // #including tuple crashed borland, so I had to give up on tie().
std::pair<CountingIterator,CountingIterator> xy(
std::equal_range(start, finish, *internal));
CountingIterator x = xy.first, y = xy.second;
assert(boost::detail::distance(x, y) == 1); assert(boost::detail::distance(x, y) == 1);
// Show that values outside the range can't be found // Show that values outside the range can't be found
@@ -234,14 +240,14 @@ int main()
test_integer<unsigned int>(); test_integer<unsigned int>();
test_integer<long>(); test_integer<long>();
test_integer<unsigned long>(); test_integer<unsigned long>();
#if defined(ULLONG_MAX) || defined(ULONG_LONG_MAX) #if defined(BOOST_HAS_LONG_LONG)
test_integer<long long>(); test_integer<long long>();
test_integer<unsigned long long>(); test_integer<unsigned long long>();
#endif #endif
// wrapping an iterator or non-built-in integer type causes an INTERNAL // wrapping an iterator or non-built-in integer type causes an INTERNAL
// COMPILER ERROR in MSVC without STLport. I'm clueless as to why. // COMPILER ERROR in MSVC without STLport. I'm clueless as to why.
#if !defined(BOOST_MSVC) || defined(__SGI_STL_PORT) #if !defined(BOOST_MSVC) || BOOST_MSVC > 1200 || defined(__SGI_STL_PORT)
// Test user-defined type. // Test user-defined type.
test_integer<my_int1>(); test_integer<my_int1>();
test_integer<my_int2>(); test_integer<my_int2>();

32
current_function_test.cpp Normal file
View File

@@ -0,0 +1,32 @@
#if defined(_MSC_VER) && !defined(__ICL)
#pragma warning(disable: 4786) // identifier truncated in debug info
#pragma warning(disable: 4710) // function not inlined
#pragma warning(disable: 4711) // function selected for automatic inline expansion
#pragma warning(disable: 4514) // unreferenced inline removed
#endif
//
// current_function_test.cpp - a test for boost/current_function.hpp
//
// Copyright (c) 2002 Peter Dimov and Multi Media Ltd.
//
// Permission to copy, use, modify, sell and distribute this software
// is granted provided this copyright notice appears in all copies.
// This software is provided "as is" without express or implied
// warranty, and with no claim as to its suitability for any purpose.
//
#include <boost/current_function.hpp>
#include <cstdio>
void message(char const * file, long line, char const * func, char const * msg)
{
std::printf("%s(%ld): %s in function '%s'\n", file, line, msg, func);
}
#define MESSAGE(msg) message(__FILE__, __LINE__, BOOST_CURRENT_FUNCTION, msg)
int main()
{
MESSAGE("assertion failed");
}

View File

@@ -195,7 +195,7 @@ The policies type has only one public function, which is its constructor:
<pre> <pre>
template &lt;class Predicate, class BaseIterator&gt; template &lt;class Predicate, class BaseIterator&gt;
typename detail::filter_generator&lt;Predicate, BaseIterator&gt;::type typename filter_generator&lt;Predicate, BaseIterator&gt;::type
make_filter_iterator(BaseIterator first, BaseIterator last, const Predicate& p = Predicate()) make_filter_iterator(BaseIterator first, BaseIterator last, const Predicate& p = Predicate())
</pre> </pre>

View File

@@ -7,7 +7,6 @@
// "as is" without express or implied warranty, and with no claim as // "as is" without express or implied warranty, and with no claim as
// to its suitability for any purpose. // to its suitability for any purpose.
#include <boost/config.hpp> #include <boost/config.hpp>
#include <algorithm> #include <algorithm>
#include <functional> #include <functional>
@@ -20,8 +19,17 @@ struct is_positive_number {
int main() int main()
{ {
int numbers[] = { 0, -1, 4, -3, 5, 8, -2 }; int numbers_[] = { 0, -1, 4, -3, 5, 8, -2 };
const int N = sizeof(numbers)/sizeof(int); const int N = sizeof(numbers_)/sizeof(int);
#ifdef BOOST_NO_STD_ITERATOR_TRAITS
// Assume there won't be proper iterator traits for pointers. This
// is just a wrapper for int* which has the right traits.
typedef boost::iterator_adaptor<int*, boost::default_iterator_policies, int> base_iterator;
#else
typedef int* base_iterator;
#endif
base_iterator numbers(numbers_);
// Example using make_filter_iterator() // Example using make_filter_iterator()
std::copy(boost::make_filter_iterator<is_positive_number>(numbers, numbers + N), std::copy(boost::make_filter_iterator<is_positive_number>(numbers, numbers + N),
@@ -30,7 +38,7 @@ int main()
std::cout << std::endl; std::cout << std::endl;
// Example using filter_iterator_generator // Example using filter_iterator_generator
typedef boost::filter_iterator_generator<is_positive_number, int*, int>::type typedef boost::filter_iterator_generator<is_positive_number, base_iterator, int>::type
FilterIter; FilterIter;
is_positive_number predicate; is_positive_number predicate;
FilterIter::policies_type policies(predicate, numbers + N); FilterIter::policies_type policies(predicate, numbers + N);

View File

@@ -135,7 +135,7 @@ private:
int main() int main()
{ {
my_generator gen; my_generator gen;
boost::generator_iterator&lt;my_generator> it(gen); boost::generator_iterator_generator&lt;my_generator&gt;::type it = boost::make_generator_iterator(gen);
for(int i = 0; i &lt; 10; ++i, ++it) for(int i = 0; i &lt; 10; ++i, ++it)
std::cout &lt;&lt; *it &lt;&lt; std::endl; std::cout &lt;&lt; *it &lt;&lt; std::endl;
} }

View File

@@ -346,7 +346,7 @@ int main()
test_integer<unsigned int>(); test_integer<unsigned int>();
test_integer<long>(); test_integer<long>();
test_integer<unsigned long>(); test_integer<unsigned long>();
#if defined(ULLONG_MAX) || defined(ULONG_LONG_MAX) #if defined(BOOST_HAS_LONG_LONG)
test_integer<long long>(); test_integer<long long>();
test_integer<unsigned long long>(); test_integer<unsigned long long>();
#endif #endif

52
include/boost/assert.hpp Normal file
View File

@@ -0,0 +1,52 @@
#ifndef BOOST_ASSERT_HPP_INCLUDED
#define BOOST_ASSERT_HPP_INCLUDED
#if _MSC_VER >= 1020
#pragma once
#endif
//
// boost/assert.hpp
//
// Copyright (c) 2001, 2002 Peter Dimov and Multi Media Ltd.
//
// Permission to copy, use, modify, sell and distribute this software
// is granted provided this copyright notice appears in all copies.
// This software is provided "as is" without express or implied
// warranty, and with no claim as to its suitability for any purpose.
//
//
// When BOOST_DEBUG is not defined, it defaults to 0 (off)
// for compatibility with programs that do not expect asserts
// in the smart pointer class templates.
//
// This default may be changed after an initial transition period.
//
#ifndef BOOST_DEBUG
#define BOOST_DEBUG 0
#endif
#if BOOST_DEBUG
#include <assert.h>
#ifndef BOOST_ASSERT
#include <boost/current_function.hpp>
bool boost_error(char const * expr, char const * func, char const * file, long line);
# define BOOST_ASSERT(expr) ((expr) || !boost_error(#expr, BOOST_CURRENT_FUNCTION, __FILE__, __LINE__) || (assert(expr), true))
#endif // #ifndef BOOST_ASSERT
#else // #if BOOST_DEBUG
#undef BOOST_ASSERT
#define BOOST_ASSERT(expr) ((void)0)
#endif // #if BOOST_DEBUG
#endif // #ifndef BOOST_ASSERT_HPP_INCLUDED

View File

@@ -0,0 +1,60 @@
#ifndef BOOST_CHECKED_DELETE_HPP_INCLUDED
#define BOOST_CHECKED_DELETE_HPP_INCLUDED
#if _MSC_VER >= 1020
#pragma once
#endif
//
// boost/checked_delete.hpp
//
// Copyright (c) 1999, 2000, 2001, 2002 boost.org
//
// Permission to copy, use, modify, sell and distribute this software
// is granted provided this copyright notice appears in all copies.
// This software is provided "as is" without express or implied
// warranty, and with no claim as to its suitability for any purpose.
//
namespace boost
{
// verify that types are complete for increased safety
template< typename T > inline void checked_delete(T * x)
{
typedef char type_must_be_complete[sizeof(T)];
delete x;
}
template< typename T > inline void checked_array_delete(T * x)
{
typedef char type_must_be_complete[sizeof(T)];
delete [] x;
}
template<class T> struct checked_deleter
{
typedef void result_type;
typedef T * argument_type;
void operator()(T * x)
{
checked_delete(x);
}
};
template<class T> struct checked_array_deleter
{
typedef void result_type;
typedef T * argument_type;
void operator()(T * x)
{
checked_array_delete(x);
}
};
} // namespace boost
#endif // #ifndef BOOST_CHECKED_DELETE_HPP_INCLUDED

View File

@@ -0,0 +1,56 @@
#ifndef BOOST_CURRENT_FUNCTION_HPP_INCLUDED
#define BOOST_CURRENT_FUNCTION_HPP_INCLUDED
#if _MSC_VER >= 1020
#pragma once
#endif
//
// boost/current_function.hpp - BOOST_CURRENT_FUNCTION
//
// Copyright (c) 2002 Peter Dimov and Multi Media Ltd.
//
// Permission to copy, use, modify, sell and distribute this software
// is granted provided this copyright notice appears in all copies.
// This software is provided "as is" without express or implied
// warranty, and with no claim as to its suitability for any purpose.
//
namespace boost
{
namespace detail
{
inline void current_function_helper()
{
#if defined(__GNUC__)
# define BOOST_CURRENT_FUNCTION __PRETTY_FUNCTION__
#elif defined(__FUNCSIG__)
# define BOOST_CURRENT_FUNCTION __FUNCSIG__
#elif defined(__BORLANDC__)
# define BOOST_CURRENT_FUNCTION __FUNC__
#elif defined(__STDC_VERSION__) && (__STDC_VERSION__ >= 199901)
# define BOOST_CURRENT_FUNCTION __func__
#else
# define BOOST_CURRENT_FUNCTION "(unknown)"
#endif
}
} // namespace detail
} // namespace boost
#endif // #ifndef BOOST_CURRENT_FUNCTION_HPP_INCLUDED

View File

@@ -34,20 +34,32 @@ namespace boost{
namespace detail{ namespace detail{
template <typename T, bool isp, bool b1, bool b2> template <typename T, bool small_>
struct ct_imp2
{
typedef const T& param_type;
};
template <typename T>
struct ct_imp2<T, true>
{
typedef const T param_type;
};
template <typename T, bool isp, bool b1>
struct ct_imp struct ct_imp
{ {
typedef const T& param_type; typedef const T& param_type;
}; };
template <typename T, bool isp> template <typename T, bool isp>
struct ct_imp<T, isp, true, true> struct ct_imp<T, isp, true>
{ {
typedef T const param_type; typedef typename ct_imp2<T, sizeof(T) <= sizeof(void*)>::param_type param_type;
}; };
template <typename T, bool b1, bool b2> template <typename T, bool b1>
struct ct_imp<T, true, b1, b2> struct ct_imp<T, true, b1>
{ {
typedef T const param_type; typedef T const param_type;
}; };
@@ -67,7 +79,11 @@ public:
// however compiler bugs prevent this - instead pass three bool's to // however compiler bugs prevent this - instead pass three bool's to
// ct_imp<T,bool,bool,bool> and add an extra partial specialisation // ct_imp<T,bool,bool,bool> and add an extra partial specialisation
// of ct_imp to handle the logic. (JM) // of ct_imp to handle the logic. (JM)
typedef typename detail::ct_imp<T, ::boost::is_pointer<typename remove_const<T>::type>::value, ::boost::is_arithmetic<typename remove_const<T>::type>::value, sizeof(T) <= sizeof(void*)>::param_type param_type; typedef typename detail::ct_imp<
T,
::boost::is_pointer<T>::value,
::boost::is_arithmetic<T>::value
>::param_type param_type;
}; };
template <typename T> template <typename T>
@@ -79,7 +95,7 @@ struct call_traits<T&>
typedef T& param_type; // hh removed const typedef T& param_type; // hh removed const
}; };
#if defined(__BORLANDC__) && (__BORLANDC__ <= 0x551) #if defined(__BORLANDC__) && (__BORLANDC__ <= 0x560)
// these are illegal specialisations; cv-qualifies applied to // these are illegal specialisations; cv-qualifies applied to
// references have no effect according to [8.3.2p1], // references have no effect according to [8.3.2p1],
// C++ Builder requires them though as it treats cv-qualified // C++ Builder requires them though as it treats cv-qualified

View File

@@ -33,7 +33,7 @@
namespace boost{ namespace boost{
#if defined(BOOST_MSVC6_MEMBER_TEMPLATES) || !defined(BOOST_NO_MEMBER_TEMPLATES) #ifdef BOOST_MSVC6_MEMBER_TEMPLATES
// //
// use member templates to emulate // use member templates to emulate
// partial specialisation: // partial specialisation:
@@ -64,7 +64,8 @@ struct reference_call_traits
typedef T const_reference; typedef T const_reference;
typedef T param_type; typedef T param_type;
}; };
template <bool simple, bool reference>
template <bool pointer, bool arithmetic, bool reference>
struct call_traits_chooser struct call_traits_chooser
{ {
template <class T> template <class T>
@@ -73,8 +74,9 @@ struct call_traits_chooser
typedef standard_call_traits<T> type; typedef standard_call_traits<T> type;
}; };
}; };
template <> template <>
struct call_traits_chooser<true, false> struct call_traits_chooser<true, false, false>
{ {
template <class T> template <class T>
struct rebind struct rebind
@@ -82,8 +84,9 @@ struct call_traits_chooser<true, false>
typedef simple_call_traits<T> type; typedef simple_call_traits<T> type;
}; };
}; };
template <> template <>
struct call_traits_chooser<false, true> struct call_traits_chooser<false, false, true>
{ {
template <class T> template <class T>
struct rebind struct rebind
@@ -91,12 +94,50 @@ struct call_traits_chooser<false, true>
typedef reference_call_traits<T> type; typedef reference_call_traits<T> type;
}; };
}; };
template <bool size_is_small>
struct call_traits_sizeof_chooser2
{
template <class T>
struct small_rebind
{
typedef simple_call_traits<T> small_type;
};
};
template<>
struct call_traits_sizeof_chooser2<false>
{
template <class T>
struct small_rebind
{
typedef standard_call_traits<T> small_type;
};
};
template <>
struct call_traits_chooser<false, true, false>
{
template <class T>
struct rebind
{
enum { sizeof_choice = (sizeof(T) <= sizeof(void*)) };
typedef call_traits_sizeof_chooser2<(sizeof(T) <= sizeof(void*))> chooser;
typedef typename chooser::template small_rebind<T> bound_type;
typedef typename bound_type::small_type type;
};
};
} // namespace detail } // namespace detail
template <typename T> template <typename T>
struct call_traits struct call_traits
{ {
private: private:
typedef detail::call_traits_chooser<(is_pointer<T>::value || is_arithmetic<T>::value) && sizeof(T) <= sizeof(void*), is_reference<T>::value> chooser; typedef detail::call_traits_chooser<
::boost::is_pointer<T>::value,
::boost::is_arithmetic<T>::value,
::boost::is_reference<T>::value
> chooser;
typedef typename chooser::template rebind<T> bound_type; typedef typename chooser::template rebind<T> bound_type;
typedef typename bound_type::type call_traits_type; typedef typename bound_type::type call_traits_type;
public: public:

View File

@@ -38,7 +38,7 @@
namespace boost namespace boost
{ {
#if defined(BOOST_MSVC6_MEMBER_TEMPLATES) || !defined(BOOST_NO_MEMBER_TEMPLATES) #ifdef BOOST_MSVC6_MEMBER_TEMPLATES
// //
// use member templates to emulate // use member templates to emulate
// partial specialisation. Note that due to // partial specialisation. Note that due to
@@ -168,7 +168,7 @@ public:
compressed_pair_1(const ::boost::compressed_pair<T1,T2>& x) compressed_pair_1(const ::boost::compressed_pair<T1,T2>& x)
: T2(x.second()), _first(x.first()) {} : T2(x.second()), _first(x.first()) {}
#ifdef BOOST_MSVC #if defined(BOOST_MSVC) && BOOST_MSVC <= 1300
// Total weirdness. If the assignment to _first is moved after // Total weirdness. If the assignment to _first is moved after
// the call to the inherited operator=, then this breaks graph/test/graph.cpp // the call to the inherited operator=, then this breaks graph/test/graph.cpp
// by way of iterator_adaptor. // by way of iterator_adaptor.

View File

@@ -9,6 +9,7 @@
// See http://www.boost.org for most recent version including documentation. // See http://www.boost.org for most recent version including documentation.
// Revision History // Revision History
// 02 Dec 01 Bug fixed in random_access_iteratable. (Helmut Zeisel)
// 28 Sep 01 Factored out iterator operator groups. (Daryle Walker) // 28 Sep 01 Factored out iterator operator groups. (Daryle Walker)
// 27 Aug 01 'left' form for non commutative operators added; // 27 Aug 01 'left' form for non commutative operators added;
// additional classes for groups of related operators added; // additional classes for groups of related operators added;
@@ -87,7 +88,7 @@ namespace boost {
namespace detail { namespace detail {
// Helmut Zeisel, empty base class optimization bug with GCC 3.0.0 // Helmut Zeisel, empty base class optimization bug with GCC 3.0.0
#if defined(__GNUCC__) && __GNUC__==3 && __GNUC_MINOR__==0 && __GNU_PATCHLEVEL__==0 #if defined(__GNUC__) && __GNUC__==3 && __GNUC_MINOR__==0 && __GNU_PATCHLEVEL__==0
class empty_base { class empty_base {
bool dummy; bool dummy;
}; };
@@ -597,10 +598,14 @@ struct bidirectional_iteratable
, decrementable<T, B , decrementable<T, B
> > {}; > > {};
// To avoid repeated derivation from equality_comparable,
// which is an indirect base class of bidirectional_iterable,
// random_access_iteratable must not be derived from totally_ordered1
// but from less_than_comparable1 only. (Helmut Zeisel, 02-Dec-2001)
template <class T, class P, class D, class R, class B = ::boost::detail::empty_base> template <class T, class P, class D, class R, class B = ::boost::detail::empty_base>
struct random_access_iteratable struct random_access_iteratable
: bidirectional_iteratable<T, P : bidirectional_iteratable<T, P
, totally_ordered1<T , less_than_comparable1<T
, additive2<T, D , additive2<T, D
, indexable<T, D, R, B , indexable<T, D, R, B
> > > > {}; > > > > {};
@@ -894,11 +899,9 @@ template <class T,
class P = V*, class P = V*,
class R = V&> class R = V&>
struct forward_iterator_helper struct forward_iterator_helper
: equality_comparable1<T : forward_iteratable<T, P
, incrementable<T
, dereferenceable<T, P
, boost::iterator<std::forward_iterator_tag, V, D, P, R , boost::iterator<std::forward_iterator_tag, V, D, P, R
> > > > {}; > > {};
template <class T, template <class T,
class V, class V,
@@ -906,11 +909,9 @@ template <class T,
class P = V*, class P = V*,
class R = V&> class R = V&>
struct bidirectional_iterator_helper struct bidirectional_iterator_helper
: equality_comparable1<T : bidirectional_iteratable<T, P
, unit_steppable<T
, dereferenceable<T, P
, boost::iterator<std::bidirectional_iterator_tag, V, D, P, R , boost::iterator<std::bidirectional_iterator_tag, V, D, P, R
> > > > {}; > > {};
template <class T, template <class T,
class V, class V,
@@ -918,13 +919,9 @@ template <class T,
class P = V*, class P = V*,
class R = V&> class R = V&>
struct random_access_iterator_helper struct random_access_iterator_helper
: totally_ordered1<T : random_access_iteratable<T, P, D, R
, unit_steppable<T
, dereferenceable<T, P
, additive2<T, D
, indexable<T, D, R
, boost::iterator<std::random_access_iterator_tag, V, D, P, R , boost::iterator<std::random_access_iterator_tag, V, D, P, R
> > > > > > > >
{ {
friend D requires_difference_operator(const T& x, const T& y) { friend D requires_difference_operator(const T& x, const T& y) {
return x - y; return x - y;

View File

@@ -1,15 +1,19 @@
#ifndef BOOST_REF_HPP_INCLUDED #ifndef BOOST_REF_HPP_INCLUDED
#define BOOST_REF_HPP_INCLUDED # define BOOST_REF_HPP_INCLUDED
#if _MSC_VER+0 >= 1020 # if _MSC_VER+0 >= 1020
#pragma once # pragma once
#endif # endif
# include <boost/config.hpp>
# include <boost/utility/addressof.hpp>
// //
// ref.hpp - ref/cref, useful helper functions // ref.hpp - ref/cref, useful helper functions
// //
// Copyright (C) 1999, 2000 Jaakko J<>rvi (jaakko.jarvi@cs.utu.fi) // Copyright (C) 1999, 2000 Jaakko J<>rvi (jaakko.jarvi@cs.utu.fi)
// Copyright (C) 2001 Peter Dimov // Copyright (C) 2001, 2002 Peter Dimov
// Copyright (C) 2002 David Abrahams
// //
// Permission to copy, use, modify, sell and distribute this software // Permission to copy, use, modify, sell and distribute this software
// is granted provided this copyright notice appears in all copies. // is granted provided this copyright notice appears in all copies.
@@ -25,25 +29,34 @@ namespace boost
template<class T> class reference_wrapper template<class T> class reference_wrapper
{ {
public: public:
typedef T type;
explicit reference_wrapper(T & t): t_(t) {} #if defined(BOOST_MSVC) && (BOOST_MSVC < 1300)
operator T & () const { return t_; } explicit reference_wrapper(T& t): t_(&t) {}
T & get() const { return t_; } #else
explicit reference_wrapper(T& t): t_(addressof(t)) {}
#endif
operator T& () const { return *t_; }
T& get() const { return *t_; }
T* get_pointer() const { return t_; }
private: private:
T & t_; T* t_;
reference_wrapper & operator= (reference_wrapper const &);
}; };
#if defined(__BORLANDC__) && (__BORLANDC__ <= 0x551) # if defined(__BORLANDC__) && (__BORLANDC__ <= 0x560)
#define BOOST_REF_CONST # define BOOST_REF_CONST
#else # else
#define BOOST_REF_CONST const # define BOOST_REF_CONST const
#endif # endif
template<class T> inline reference_wrapper<T> BOOST_REF_CONST ref(T & t) template<class T> inline reference_wrapper<T> BOOST_REF_CONST ref(T & t)
{ {
@@ -55,7 +68,94 @@ template<class T> inline reference_wrapper<T const> BOOST_REF_CONST cref(T const
return reference_wrapper<T const>(t); return reference_wrapper<T const>(t);
} }
#undef BOOST_REF_CONST # undef BOOST_REF_CONST
# ifndef BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION
template<typename T>
class is_reference_wrapper
{
public:
BOOST_STATIC_CONSTANT(bool, value = false);
};
template<typename T>
class is_reference_wrapper<reference_wrapper<T> >
{
public:
BOOST_STATIC_CONSTANT(bool, value = true);
};
template<typename T>
class unwrap_reference
{
public:
typedef T type;
};
template<typename T>
class unwrap_reference<reference_wrapper<T> >
{
public:
typedef T type;
};
# else // no partial specialization
} // namespace boost
#include <boost/type.hpp>
namespace boost
{
namespace detail
{
typedef char (&yes_reference_wrapper_t)[1];
typedef char (&no_reference_wrapper_t)[2];
no_reference_wrapper_t is_reference_wrapper_test(...);
template<typename T>
yes_reference_wrapper_t is_reference_wrapper_test(type< reference_wrapper<T> >);
template<bool wrapped>
struct reference_unwrapper
{
template <class T>
struct apply
{
typedef T type;
};
};
template<>
struct reference_unwrapper<true>
{
template <class T>
struct apply
{
typedef typename T::type type;
};
};
}
template<typename T>
class is_reference_wrapper
{
public:
BOOST_STATIC_CONSTANT(
bool, value = (
sizeof(detail::is_reference_wrapper_test(type<T>()))
== sizeof(detail::yes_reference_wrapper_t)));
};
template <typename T>
class unwrap_reference
: public detail::reference_unwrapper<
is_reference_wrapper<T>::value
>::template apply<T>
{};
# endif // BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION
} // namespace boost } // namespace boost

View File

@@ -13,37 +13,14 @@
#ifndef BOOST_UTILITY_HPP #ifndef BOOST_UTILITY_HPP
#define BOOST_UTILITY_HPP #define BOOST_UTILITY_HPP
#include <boost/config.hpp> // broken compiler workarounds
#include <boost/static_assert.hpp>
// certain headers are part of the <utility.hpp> interface // certain headers are part of the <utility.hpp> interface
#include <boost/utility/base_from_member.hpp>
#include <cstddef> // for size_t #include <boost/checked_delete.hpp>
#include <utility> // for std::pair #include <boost/utility/base_from_member.hpp>
#include <boost/utility/addressof.hpp>
namespace boost namespace boost
{ {
// checked_delete() and checked_array_delete() -----------------------------//
// verify that types are complete for increased safety
template< typename T >
inline void checked_delete(T * x)
{
BOOST_STATIC_ASSERT( sizeof(T) != 0 ); // assert type complete at point
// of instantiation
delete x;
}
template< typename T >
inline void checked_array_delete(T * x)
{
BOOST_STATIC_ASSERT( sizeof(T) != 0 ); // assert type complete at point
// of instantiation
delete [] x;
}
// next() and prior() template functions -----------------------------------// // next() and prior() template functions -----------------------------------//
// Helper functions for classes like bidirectional iterators not supporting // Helper functions for classes like bidirectional iterators not supporting

View File

@@ -0,0 +1,31 @@
// Copyright (C) 2002 Brad King (brad.king@kitware.com)
// Doug Gregor (gregod@cs.rpi.edu)
// Peter Dimov
//
// Permission to copy, use, sell and distribute this software is granted
// provided this copyright notice appears in all copies.
// Permission to modify the code and to distribute modified code is granted
// provided this copyright notice appears in all copies, and a notice
// that the code was modified is included with the copyright notice.
//
// This software is provided "as is" without express or implied warranty,
// and with no claim as to its suitability for any purpose.
// For more information, see http://www.boost.org
#ifndef BOOST_UTILITY_ADDRESSOF_HPP
#define BOOST_UTILITY_ADDRESSOF_HPP
namespace boost {
// Do not make addressof() inline. Breaks MSVC 7. (Peter Dimov)
template <typename T> T* addressof(T& v)
{
return reinterpret_cast<T*>(
&const_cast<char&>(reinterpret_cast<const volatile char &>(v)));
}
}
#endif // BOOST_UTILITY_ADDRESSOF_HPP

34
index.html Normal file
View File

@@ -0,0 +1,34 @@
<html>
<head>
<meta http-equiv="Content-Language" content="en-us">
<meta name="GENERATOR" content="Microsoft FrontPage 5.0">
<meta name="ProgId" content="FrontPage.Editor.Document">
<meta http-equiv="Content-Type" content="text/html; charset=windows-1252">
<title>Boost Utility Library</title>
</head>
<body bgcolor="#FFFFFF">
<h1><IMG SRC="../../c++boost.gif" WIDTH="276" HEIGHT="86" align="center">Boost
Utility Library</h1>
<p>The Boost Utility Library isn't really a single library at all.&nbsp; It is
just a collection for components too small to be called libraries in their own
right.</p>
<p>But that doesn't mean there isn't useful stuff here.&nbsp; Take a look:</p>
<blockquote>
<p><a href="base_from_member.html">base_from_member</a><br>
<a href="call_traits.htm">call_traits.htm</a><br>
<a href="compressed_pair.htm">compressed_pair.htm</a><br>
<a href="operators.htm">operators.htm</a><br>
<a href="tie.html">tie</a><br>
<a href="utility.htm">utility.htm</a></p>
</blockquote>
<hr>
<p>Revised
<!--webbot bot="Timestamp" S-Type="EDITED" S-Format="%d %B, %Y" startspan -->07 May, 2002<!--webbot bot="Timestamp" endspan i-checksum="13976" --></p>
<p>&nbsp;</p>
</body>
</html>

View File

@@ -51,7 +51,7 @@ int main(int, char*[])
// Example of using make_indirect_iterator() // Example of using make_indirect_iterator()
#ifndef BOOST_MSVC #if !defined(BOOST_MSVC) || BOOST_MSVC > 1300
std::copy(boost::make_indirect_iterator(pointers_to_chars), std::copy(boost::make_indirect_iterator(pointers_to_chars),
boost::make_indirect_iterator(pointers_to_chars + N), boost::make_indirect_iterator(pointers_to_chars + N),
std::ostream_iterator<char>(std::cout, ",")); std::ostream_iterator<char>(std::cout, ","));

View File

@@ -31,7 +31,7 @@ typedef std::set<storage::iterator> iterator_set;
void more_indirect_iterator_tests() void more_indirect_iterator_tests()
{ {
// For some reason all heck breaks loose in the compiler under these conditions. // For some reason all heck breaks loose in the compiler under these conditions.
#if !defined(BOOST_MSVC) || !defined(__STL_DEBUG) #if !defined(BOOST_MSVC) || BOOST_MSVC > 1200 || !defined(__STL_DEBUG)
storage store(1000); storage store(1000);
std::generate(store.begin(), store.end(), rand); std::generate(store.begin(), store.end(), rand);
@@ -46,7 +46,7 @@ void more_indirect_iterator_tests()
typedef boost::indirect_iterator_pair_generator< typedef boost::indirect_iterator_pair_generator<
pointer_deque::iterator pointer_deque::iterator
#ifdef BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION #ifdef BOOST_NO_STD_ITERATOR_TRAITS
, int , int
#endif #endif
> IndirectDeque; > IndirectDeque;
@@ -75,7 +75,7 @@ void more_indirect_iterator_tests()
typedef boost::indirect_iterator_generator< typedef boost::indirect_iterator_generator<
iterator_set::iterator iterator_set::iterator
#ifdef BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION #ifdef BOOST_NO_STD_ITERATOR_TRAITS
, int , int
#endif #endif
>::type indirect_set_iterator; >::type indirect_set_iterator;
@@ -117,7 +117,7 @@ main()
ptr[k] = array + k; ptr[k] = array + k;
typedef boost::indirect_iterator_generator<dummyT** typedef boost::indirect_iterator_generator<dummyT**
#ifdef BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION #ifdef BOOST_NO_STD_ITERATOR_TRAITS
, dummyT , dummyT
#endif #endif
>::type indirect_iterator; >::type indirect_iterator;
@@ -127,7 +127,7 @@ main()
indirect_iterator i(ptr); indirect_iterator i(ptr);
boost::random_access_iterator_test(i, N, array); boost::random_access_iterator_test(i, N, array);
#ifndef BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION #ifndef BOOST_NO_STD_ITERATOR_TRAITS
boost::random_access_iterator_test(boost::make_indirect_iterator(ptr), N, array); boost::random_access_iterator_test(boost::make_indirect_iterator(ptr), N, array);
#endif #endif
@@ -139,7 +139,7 @@ main()
dummyT*const* const_ptr = ptr; dummyT*const* const_ptr = ptr;
#ifndef BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION #ifndef BOOST_NO_STD_ITERATOR_TRAITS
boost::random_access_iterator_test(boost::make_indirect_iterator(const_ptr), N, array); boost::random_access_iterator_test(boost::make_indirect_iterator(const_ptr), N, array);
#endif #endif
boost::const_nonconst_iterator_test(i, ++j); boost::const_nonconst_iterator_test(i, ++j);

View File

@@ -133,7 +133,7 @@ main()
boost::function_requires< boost::function_requires<
boost::RandomAccessIteratorPoliciesConcept< boost::RandomAccessIteratorPoliciesConcept<
boost::default_iterator_policies, boost::default_iterator_policies,
boost::iterator_adaptor<int*, boost::default_iterator_policies>, boost::iterator_adaptor<storage::iterator, boost::default_iterator_policies>,
boost::iterator<std::random_access_iterator_tag, int, std::ptrdiff_t, boost::iterator<std::random_access_iterator_tag, int, std::ptrdiff_t,
int*, int&> int*, int&>
> >(); > >();
@@ -156,7 +156,7 @@ main()
boost::default_iterator_policies, boost::default_iterator_policies,
boost::value_type_is<const int> > Iter1; boost::value_type_is<const int> > Iter1;
BOOST_STATIC_ASSERT((boost::is_same<Iter1::value_type, int>::value)); BOOST_STATIC_ASSERT((boost::is_same<Iter1::value_type, int>::value));
#if defined(__BORLANDC__) || defined(BOOST_MSVC) #if defined(__BORLANDC__) || defined(BOOST_MSVC) && BOOST_MSVC <= 1300
// We currently don't know how to workaround this bug. // We currently don't know how to workaround this bug.
BOOST_STATIC_ASSERT((boost::is_same<Iter1::reference, int&>::value)); BOOST_STATIC_ASSERT((boost::is_same<Iter1::reference, int&>::value));
BOOST_STATIC_ASSERT((boost::is_same<Iter1::pointer, int*>::value)); BOOST_STATIC_ASSERT((boost::is_same<Iter1::pointer, int*>::value));
@@ -224,7 +224,7 @@ main()
std::reverse(reversed, reversed + N); std::reverse(reversed, reversed + N);
typedef boost::reverse_iterator_generator<dummyT* typedef boost::reverse_iterator_generator<dummyT*
#ifdef BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION #if defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION) || defined(BOOST_NO_STD_ITERATOR_TRAITS)
, dummyT , dummyT
#endif #endif
>::type reverse_iterator; >::type reverse_iterator;
@@ -232,12 +232,12 @@ main()
reverse_iterator i(reversed + N); reverse_iterator i(reversed + N);
boost::random_access_iterator_test(i, N, array); boost::random_access_iterator_test(i, N, array);
#ifndef BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION #if !defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION) && !defined(BOOST_NO_STD_ITERATOR_TRAITS)
boost::random_access_iterator_test(boost::make_reverse_iterator(reversed + N), N, array); boost::random_access_iterator_test(boost::make_reverse_iterator(reversed + N), N, array);
#endif #endif
typedef boost::reverse_iterator_generator<const dummyT* typedef boost::reverse_iterator_generator<const dummyT*
#ifdef BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION #if defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION) || defined(BOOST_NO_STD_ITERATOR_TRAITS)
, dummyT, const dummyT&, const dummyT , dummyT, const dummyT&, const dummyT
#endif #endif
>::type const_reverse_iterator; >::type const_reverse_iterator;
@@ -247,7 +247,7 @@ main()
const dummyT* const_reversed = reversed; const dummyT* const_reversed = reversed;
#ifndef BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION #if !defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION) && !defined(BOOST_NO_STD_ITERATOR_TRAITS)
boost::random_access_iterator_test(boost::make_reverse_iterator(const_reversed + N), N, array); boost::random_access_iterator_test(boost::make_reverse_iterator(const_reversed + N), N, array);
#endif #endif
@@ -282,7 +282,7 @@ main()
// Many compilers' builtin deque iterators don't interoperate well, though // Many compilers' builtin deque iterators don't interoperate well, though
// STLport fixes that problem. // STLport fixes that problem.
#if defined(__SGI_STL_PORT) || !defined(__GNUC__) && !defined(__BORLANDC__) && !defined(BOOST_MSVC) #if defined(__SGI_STL_PORT) || !defined(__GNUC__) && !defined(__BORLANDC__) && (!defined(BOOST_MSVC) || BOOST_MSVC > 1200)
boost::const_nonconst_iterator_test(i, ++j); boost::const_nonconst_iterator_test(i, ++j);
#endif #endif
} }
@@ -300,7 +300,7 @@ main()
typedef boost::detail::non_bidirectional_category<dummyT*>::type category; typedef boost::detail::non_bidirectional_category<dummyT*>::type category;
typedef boost::filter_iterator_generator<one_or_four, dummyT* typedef boost::filter_iterator_generator<one_or_four, dummyT*
#ifdef BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION #if defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION) || defined(BOOST_NO_STD_ITERATOR_TRAITS)
, dummyT , dummyT
#endif #endif
>::type filter_iter; >::type filter_iter;
@@ -327,7 +327,7 @@ main()
// On compilers not supporting partial specialization, we can do more type // On compilers not supporting partial specialization, we can do more type
// deduction with deque iterators than with pointers... unless the library // deduction with deque iterators than with pointers... unless the library
// is broken ;-( // is broken ;-(
#if !defined(BOOST_MSVC) || defined(__SGI_STL_PORT) #if !defined(BOOST_MSVC) || BOOST_MSVC > 1200 || defined(__SGI_STL_PORT)
std::deque<dummyT> array2; std::deque<dummyT> array2;
std::copy(array+0, array+N, std::back_inserter(array2)); std::copy(array+0, array+N, std::back_inserter(array2));
boost::forward_iterator_test( boost::forward_iterator_test(
@@ -339,7 +339,7 @@ main()
dummyT(1), dummyT(4)); dummyT(1), dummyT(4));
#endif #endif
#if !defined(BOOST_MSVC) // This just freaks MSVC out completely #if !defined(BOOST_MSVC) || BOOST_MSVC > 1200 // This just freaks MSVC out completely
boost::forward_iterator_test( boost::forward_iterator_test(
boost::make_filter_iterator<one_or_four>( boost::make_filter_iterator<one_or_four>(
boost::make_reverse_iterator(array2.end()), boost::make_reverse_iterator(array2.end()),
@@ -348,7 +348,7 @@ main()
dummyT(4), dummyT(1)); dummyT(4), dummyT(1));
#endif #endif
#ifndef BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION #if !defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION) && !defined(BOOST_NO_STD_ITERATOR_TRAITS)
boost::forward_iterator_test( boost::forward_iterator_test(
boost::make_filter_iterator(array+0, array+N, one_or_four()), boost::make_filter_iterator(array+0, array+N, one_or_four()),
dummyT(1), dummyT(4)); dummyT(1), dummyT(4));
@@ -409,17 +409,31 @@ main()
{ {
// check permutation_iterator // check permutation_iterator
typedef std::vector< int > element_range_type; typedef std::deque< int > element_range_type;
typedef std::list< int > index_type; typedef std::list< int > index_type;
static const int element_range_size = 10; static const int element_range_size = 10;
static const int index_size = 4; static const int index_size = 4;
element_range_type elements( element_range_size ); element_range_type elements( element_range_size );
std::iota( elements.begin(), elements.end(), 0 );
for(element_range_type::iterator el_it = elements.begin();
el_it != elements.end();
++el_it)
{
*el_it = std::distance( elements.begin(), el_it );
}
index_type indices( index_size ); index_type indices( index_size );
std::iota( indices.begin(), indices.end(), element_range_size - index_size );
for(index_type::iterator i_it = indices.begin();
i_it != indices.end();
++i_it)
{
*i_it = element_range_size - index_size
+ std::distance(indices.begin(), i_it );
}
std::reverse( indices.begin(), indices.end() ); std::reverse( indices.begin(), indices.end() );
typedef boost::permutation_iterator_generator< element_range_type::iterator, index_type::iterator >::type permutation_type; typedef boost::permutation_iterator_generator< element_range_type::iterator, index_type::iterator >::type permutation_type;

View File

@@ -92,6 +92,8 @@
<li><a href="#declaration_synopsis">Declaration Synopsis</a> <li><a href="#declaration_synopsis">Declaration Synopsis</a>
<li><a href="#portability">Portability</a>
<li><a href="#notes">Notes</a> <li><a href="#notes">Notes</a>
</ul> </ul>
@@ -182,7 +184,7 @@ struct iterator_adaptor;
<p>Although <tt>iterator_adaptor</tt> takes seven template parameters, <p>Although <tt>iterator_adaptor</tt> takes seven template parameters,
defaults have been carefully chosen to minimize the number of parameters defaults have been carefully chosen to minimize the number of parameters
you must supply in most cases, especially if <tt>BaseType</tt> is an you must supply in most cases, especially if <tt>Base</tt> is an
iterator. iterator.
<table border="1" summary="iterator_adaptor template parameters"> <table border="1" summary="iterator_adaptor template parameters">
@@ -191,17 +193,26 @@ struct iterator_adaptor;
<th>Description <th>Description
<tr> <th>Requirements
<td><tt>BaseType</tt>
<td>The type being wrapped. <tr>
<td><tt>Base</tt>
<td>The data type on which the resulting iterator is based. Do
not be misled by the name &quot;Base&quot;: this is not a base
class.
<td>
<a href="http://www.sgi.com/tech/stl/Assignable.html">Assignable</a>,
<a href="http://www.sgi.com/tech/stl/DefaultConstructible.html">Default&nbsp;Constructible</a>
<tr> <tr>
<td><tt>Policies</tt> <td><tt>Policies</tt>
<td>A <a href="../../more/generic_programming.html#policy">policy <td>A <a href="../../more/generic_programming.html#policy">policy
class</a> that supplies core functionality to the resulting iterator. A class</a> that supplies core functionality to the resulting iterator.
detailed description can be found <a href="#policies">below</a>.
<td>See table <a href="#policies">below</a>.
<tr> <tr>
<td><tt>Value</tt> <td><tt>Value</tt>
@@ -212,7 +223,7 @@ struct iterator_adaptor;
"#1">[1]</a>. If the <tt>value_type</tt> you wish to use is an abstract "#1">[1]</a>. If the <tt>value_type</tt> you wish to use is an abstract
base class see note <a href="#5">[5]</a>.<br> base class see note <a href="#5">[5]</a>.<br>
<b>Default:</b> <b>Default:</b>
<tt>std::iterator_traits&lt;BaseType&gt;::value_type</tt> <a href= <tt>std::iterator_traits&lt;Base&gt;::value_type</tt> <a href=
"#2">[2]</a> "#2">[2]</a>
<tr> <tr>
@@ -222,29 +233,52 @@ struct iterator_adaptor;
particular, the result type of <tt>operator*()</tt>.<br> particular, the result type of <tt>operator*()</tt>.<br>
<b>Default:</b> If <tt>Value</tt> is supplied, <tt>Value&amp;</tt> is <b>Default:</b> If <tt>Value</tt> is supplied, <tt>Value&amp;</tt> is
used. Otherwise used. Otherwise
<tt>std::iterator_traits&lt;BaseType&gt;::reference</tt> is used. <a href="#7">[7]</a> <tt>std::iterator_traits&lt;Base&gt;::reference</tt> is used. <a href="#7">[7]</a>
<td><a
href="http://www.sgi.com/tech/stl/ForwardIterator.html">ForwardIterators</a>,
<a
href="http://www.sgi.com/tech/stl/BidirectionalIterator.html">BidirectionalIterators</a>,
and <a
href="http://www.sgi.com/tech/stl/RandomAccessIterator.html">RandomAccessIterators</a>
require that Reference is a true reference type (e.g. not a proxy).
<tr> <tr>
<td><tt>Pointer</tt> <td><tt>Pointer</tt>
<td>The <tt>pointer</tt> type of the resulting iterator, and in <td>The <tt>pointer</tt> type of the resulting iterator, and in
particular, the result type of <tt>operator-&gt;()</tt>.<br> particular, the result type of <tt>operator-&gt;()</tt>.<br>
<b>Default:</b> If <tt>Value</tt> was supplied, then <tt>Value*</tt>, <b>Default:</b> If <tt>Value</tt> was not supplied, <tt>std::iterator_traits&lt;Base&gt;::pointer</tt>. <a
otherwise <tt>std::iterator_traits&lt;BaseType&gt;::pointer</tt>. <a href="#7">[7]</a> href="#7">[7]</a> Otherwise, if <code>iterator_category</code> is
<code>input_iterator</code>, then a class yielding
<tt>Value*</tt> when <code>operator-&gt;()</code> is applied.
Otherwise, <tt>Value*</tt>.
<td><code>value_type*</code> or a
class which yields <code>value_type*</code> when
<code>operator-&gt;()</code> is applied.
<tr> <tr>
<td><tt>Category</tt> <td><tt>Category</tt>
<td>The <tt>iterator_category</tt> type for the resulting iterator.<br> <td>The <tt>iterator_category</tt> type for the resulting iterator.<br>
<b>Default:</b> <b>Default:</b>
<tt>std::iterator_traits&lt;BaseType&gt;::iterator_category</tt> <tt>std::iterator_traits&lt;Base&gt;::iterator_category</tt>
<td>One of
<code>std::input_iterator_tag</code>,
<code>std::output_iterator_tag</code>,
<code>std::forward_iterator_tag</code>,
<code>std::bidirectional_iterator_tag</code>, or
<code>std::random_access_iterator_tag</code>.
<tr> <tr>
<td><tt>Distance</tt> <td><tt>Distance</tt>
<td>The <tt>difference_type</tt> for the resulting iterator.<br> <td>The <tt>difference_type</tt> for the resulting iterator.<br>
<b>Default:</b> <b>Default:</b>
<tt>std::iterator_traits&lt;BaseType&gt;::difference_type</tt> <tt>std::iterator_traits&lt;Base&gt;::difference_type</tt>
<td>A signed integral type
<tr> <tr>
<td><tt>NamedParam</tt> <td><tt>NamedParam</tt>
@@ -307,12 +341,16 @@ typedef iterator_adaptor&lt;foo_iterator, foo_policies,
<table border="1" summary="iterator_adaptor Policies operations"> <table border="1" summary="iterator_adaptor Policies operations">
<caption> <caption>
<b>Core Iterator Operations</b><br> <b>Policies Class Requirements</b><br>
<tt>T</tt>: adapted iterator type; <tt>p</tt>: object of type T; <tt>n</tt>: <tt>T::size_type</tt>; <tt>x</tt>: <tt>T::difference_type</tt>; <tt>p1</tt>, <tt>p2</tt>: iterators <tt><b>T</b></tt>: adapted iterator type; <tt><b>x, y</b></tt>: objects of type
T; <tt><b>p</b></tt>: <tt>T::policies_type</tt>
<tt><b>d</b></tt>:
<tt>T::difference_type</tt>; <tt><b>i1</b></tt>, <tt><b>i2</b></tt>:
<tt>T::base_type</tt>
</caption> </caption>
<tr> <tr>
<th>Operation <th>Expression
<th>Effects <th>Effects
@@ -321,7 +359,7 @@ typedef iterator_adaptor&lt;foo_iterator, foo_policies,
<th>Required for Iterator Categories <th>Required for Iterator Categories
<tr> <tr>
<td><tt>initialize</tt> <td nowrap><tt>p.initialize(b)</tt>
<td>optionally modify base iterator during iterator construction <td>optionally modify base iterator during iterator construction
@@ -333,79 +371,66 @@ typedef iterator_adaptor&lt;foo_iterator, foo_policies,
"http://www.sgi.com/tech/stl/ForwardIterator.html">Forward</a>/ <a "http://www.sgi.com/tech/stl/ForwardIterator.html">Forward</a>/ <a
href= href=
"http://www.sgi.com/tech/stl/BidirectionalIterator.html">Bidirectional</a>/ "http://www.sgi.com/tech/stl/BidirectionalIterator.html">Bidirectional</a>/
<a href="http://www.sgi.com/tech/stl/RandomAccessIterator.html">Random <a href="http://www.sgi.com/tech/stl/RandomAccessIterator.html">Random&nbsp;Access</a>
Access</a>
<tr> <tr>
<td><tt>dereference</tt> <td nowrap><tt>p.dereference(x)</tt>
<td>returns an element of the iterator's <tt>reference</tt> type <td>returns an element of the iterator's <tt>reference</tt> type
<td><tt>*p</tt>, <tt>p[n]</tt> <td><tt>*x</tt>, <tt>x[d]</tt>
<tr> <tr>
<td><tt>equal</tt> <td nowrap><tt>p.equal(x, y)</tt>
<td>tests the iterator for equality <td>tests the iterator for equality
<td><tt>p1&nbsp;==&nbsp;p2</tt>, <tt>p1&nbsp;!=&nbsp;p2</tt> <td><tt>i1&nbsp;==&nbsp;i2</tt>, <tt>i1&nbsp;!=&nbsp;i2</tt>
<tr> <tr>
<td><tt>increment</tt> <td nowrap><tt>p.increment(x)</tt>
<td>increments the iterator <td>increments the iterator
<td><tt>++p</tt>, <tt>p++</tt> <td><tt>++x</tt>, <tt>x++</tt>
<tr> <tr>
<td><tt>decrement</tt> <td nowrap><tt>p.decrement(x)</tt>
<td>decrements the iterator <td>decrements the iterator
<td><tt>--p</tt>, <tt>p--</tt> <td><tt>--x</tt>, <tt>x--</tt>
<td><a href= <td><a href=
"http://www.sgi.com/tech/stl/BidirectionalIterator.html">Bidirectional</a>/ "http://www.sgi.com/tech/stl/BidirectionalIterator.html">Bidirectional</a>/
<a href="http://www.sgi.com/tech/stl/RandomAccessIterator.html">Random <a href="http://www.sgi.com/tech/stl/RandomAccessIterator.html">Random&nbsp;Access</a>
Access</a>
<tr> <tr>
<td><tt>less</tt> <td nowrap><tt>p.distance(x, y)</tt>
<td>imposes a <a href= <td>measures the distance between iterators
"http://www.sgi.com/tech/stl/StrictWeakOrdering.html">Strict Weak
Ordering</a> relation on iterators
<td> <td><tt>y&nbsp;-&nbsp;x</tt>, <tt>x&nbsp;&lt;&nbsp;y</tt>
<tt>p1&nbsp;&lt;&nbsp;p2</tt>,
<tt>p1&nbsp;&lt;=&nbsp;p2</tt>,
<tt>p1&nbsp;&gt;&nbsp;p2</tt>,
<tt>p1&nbsp;&gt;=&nbsp;p2</tt>
<td rowspan="3"><a href= <td rowspan="2"><a href=
"http://www.sgi.com/tech/stl/RandomAccessIterator.html">Random "http://www.sgi.com/tech/stl/RandomAccessIterator.html">Random
Access</a> Access</a>
<tr> <tr>
<td><tt>distance</tt> <td nowrap><tt>p.advance(x, n)</tt>
<td>measures the distance between iterators
<td><tt>p1 - p2</tt>
<tr>
<td><tt>advance</tt>
<td>adds an integer offset to iterators <td>adds an integer offset to iterators
<td> <td>
<tt>p&nbsp;+&nbsp;x</tt>, <tt>x&nbsp;+&nbsp;d</tt>,
<tt>x&nbsp;+&nbsp;p</tt>, <tt>d&nbsp;+&nbsp;x</tt>,
<tt>p&nbsp;+=&nbsp;x</tt>,
<tt>p&nbsp;-&nbsp;x</tt>, <br>
<tt>p&nbsp;-=&nbsp;x</tt> <tt>x&nbsp;+=&nbsp;d</tt>,
<tt>x&nbsp;-&nbsp;d</tt>,<br>
<tt>x&nbsp;-=&nbsp;d</tt>
</table> </table>
@@ -496,9 +521,24 @@ struct <a name="default_iterator_policies">default_iterator_policies</a>
Requires: <tt>B</tt> is convertible to <tt>Base</tt>. Requires: <tt>B</tt> is convertible to <tt>Base</tt>.
<tr> <tr>
<td><tt>base_type base() const;</tt> <td><tt>const base_type& base() const;</tt>
<br><br> <br><br>
Return a copy of the base object. Return a const reference to the base object.
<tr> <td><tt>base_type& base();</tt>
<br><br>
Return a reference to the base object. This is to give the policies object
access to the base object. See <a href="#policies">above</a> for policies
iterator_adaptor interaction.<a href="#8">[8]</a>
<tr>
<td><tt>const Policies& policies() const;</tt>
<br><br>
Return a const reference to the policies object.
<tr> <td><tt>Policies& policies();</tt>
<br><br>
Return a reference to the policies object.
</table> </table>
<h3><a name="example">Example</a></h3> <h3><a name="example">Example</a></h3>
@@ -516,7 +556,7 @@ struct <a name="default_iterator_policies">default_iterator_policies</a>
argument and that we'll need to be able to deduce the <tt>result_type</tt> argument and that we'll need to be able to deduce the <tt>result_type</tt>
of the function so we can use it for the adapted iterator's of the function so we can use it for the adapted iterator's
<tt>value_type</tt>. <a href= <tt>value_type</tt>. <a href=
"http://www.sgi.com/Technology/STL/AdaptableUnaryFunction.html">AdaptableUnaryFunction</a> "http://www.sgi.com/tech/stl/AdaptableUnaryFunction.html">AdaptableUnaryFunction</a>
is the <a href="../../more/generic_programming.html#concept">Concept</a> is the <a href="../../more/generic_programming.html#concept">Concept</a>
that fulfills those requirements. that fulfills those requirements.
@@ -665,7 +705,7 @@ int main(int, char*[])
<li>Interoperable iterators can be freely mixed in comparison expressions <li>Interoperable iterators can be freely mixed in comparison expressions
so long as the <tt>Policies</tt> class has <tt>equal</tt> (and, for so long as the <tt>Policies</tt> class has <tt>equal</tt> (and, for
random access iterators, <tt>less</tt>) members that can accept both random access iterators, <tt>distance</tt>) members that can accept both
<tt>Base</tt> types in either order. <tt>Base</tt> types in either order.
<li>Interoperable iterators can be freely mixed in subtraction <li>Interoperable iterators can be freely mixed in subtraction
@@ -719,11 +759,12 @@ they share the same <tt>Policies</tt> and since <tt>Category</tt> and
the projection <tt>const_iterator</tt>. the projection <tt>const_iterator</tt>.
<li> Since <tt>projection_iterator_policies</tt> implements only the <li> Since <tt>projection_iterator_policies</tt> implements only the
<tt>dereference</tt> operation, and inherits all other behaviors from <tt><a <tt>dereference</tt> operation, and inherits all other behaviors from
href="#default_iterator_policies">default_iterator_policies</a></tt>, which has <tt><a
fully-templatized <tt>equal</tt>, <tt>less</tt>, and <tt>distance</tt> href="#default_iterator_policies">default_iterator_policies</a></tt>,
operations, the <tt>iterator</tt> and <tt>const_iterator</tt> can be freely which has fully-templatized <tt>equal</tt> and <tt>distance</tt>
mixed in comparison and subtraction expressions. operations, the <tt>iterator</tt> and <tt>const_iterator</tt> can be
freely mixed in comparison and subtraction expressions.
</ul> </ul>
@@ -731,7 +772,7 @@ mixed in comparison and subtraction expressions.
<p>There is an unlimited number of ways the <tt>iterator_adaptors</tt> <p>There is an unlimited number of ways the <tt>iterator_adaptors</tt>
class can be used to create iterators. One interesting exercise would be to class can be used to create iterators. One interesting exercise would be to
re-implement the iterators of <tt>std::list</tt> and <tt>std::slist</tt> re-implement the iterators of <tt>std::list</tt> and <tt>slist</tt>
using <tt>iterator_adaptors</tt>, where the adapted <tt>Iterator</tt> types using <tt>iterator_adaptors</tt>, where the adapted <tt>Iterator</tt> types
would be node pointers. would be node pointers.
@@ -768,7 +809,8 @@ struct iterator_adaptor
iterator_adaptor(); iterator_adaptor();
explicit iterator_adaptor(const Base&amp;, const Policies&amp; = Policies()); explicit iterator_adaptor(const Base&amp;, const Policies&amp; = Policies());
base_type base() const; base_type& base();
const base_type& base() const;
template &lt;class B, class V, class R, class P&gt; template &lt;class B, class V, class R, class P&gt;
iterator_adaptor( iterator_adaptor(
@@ -813,6 +855,19 @@ bool operator==(const iterator_adaptor&lt;B1,P,V1,R1,P1,C,D&gt;&amp;,
// and similarly for operators !=, &lt;, &lt;=, &gt;=, &gt; // and similarly for operators !=, &lt;, &lt;=, &gt;=, &gt;
</pre> </pre>
<h3><a name="portability">Portability</a></h3>
<p>Generally, the iterator adaptors library can be compiled with all compilers
supporting iterator traits and type traits.</p>
<p>Microsoft VC++ is not able to handle iterator adaptors based on a
<code>vector<T>::iterator</code> without specifying all template paramters explicitly.
In case not all template parameters are specified explicitly, the iterator adaptors
library will deduce these types using iterator_traits. But since in VC++ a
<code>vector<T>::iterator</code> is a <code>T*</code>, VC++ can't handle using
iterator_traits due to the lack of partial template specialization.</p>
<h3><a name="notes">Notes</a></h3> <h3><a name="notes">Notes</a></h3>
<p><a name="1">[1]</a> The standard specifies that the <tt>value_type</tt> <p><a name="1">[1]</a> The standard specifies that the <tt>value_type</tt>
@@ -899,11 +954,15 @@ bool operator==(const iterator_adaptor&lt;B1,P,V1,R1,P1,C,D&gt;&amp;,
<tt>Base</tt> type is a const pointer, then the correct defaults <tt>Base</tt> type is a const pointer, then the correct defaults
for the <tt>reference</tt> and <tt>pointer</tt> types can not be for the <tt>reference</tt> and <tt>pointer</tt> types can not be
deduced. You must specify these types explicitly. deduced. You must specify these types explicitly.
<p><a name="8">[8]</a>
Exposing the base object might be considered as being dangerous.
A possible fix would require compiler support for template friends.
As this is not widely available today, the base object remains exposed for now.
<hr> <hr>
<p>Revised <p>Revised
<!--webbot bot="Timestamp" s-type="EDITED" s-format="%d %b %Y" startspan -->18 Sep 2001<!--webbot bot="Timestamp" endspan i-checksum="14941" --> <!--webbot bot="Timestamp" s-type="EDITED" s-format="%d %b %Y" startspan -->30 Nov 2001<!--webbot bot="Timestamp" endspan i-checksum="15239" -->
<p>&copy; Copyright Dave Abrahams and Jeremy Siek 2001. Permission to copy, <p>&copy; Copyright Dave Abrahams and Jeremy Siek 2001. Permission to copy,

View File

@@ -85,15 +85,17 @@ template <class Iterator,
struct non_portable_tests struct non_portable_tests
{ {
// Unfortunately, the VC6 standard library doesn't supply these :( // Unfortunately, the VC6 standard library doesn't supply these :(
typedef typename boost::detail::iterator_traits<Iterator>::pointer test_pt;
typedef typename boost::detail::iterator_traits<Iterator>::reference test_rt;
BOOST_STATIC_ASSERT(( BOOST_STATIC_ASSERT((
boost::is_same< ::boost::is_same<
typename boost::detail::iterator_traits<Iterator>::pointer, test_pt,
pointer pointer
>::value)); >::value));
BOOST_STATIC_ASSERT(( BOOST_STATIC_ASSERT((
boost::is_same< ::boost::is_same<
typename boost::detail::iterator_traits<Iterator>::reference, test_rt,
reference reference
>::value)); >::value));
}; };
@@ -102,15 +104,17 @@ template <class Iterator,
class value_type, class difference_type, class pointer, class reference, class category> class value_type, class difference_type, class pointer, class reference, class category>
struct portable_tests struct portable_tests
{ {
typedef typename boost::detail::iterator_traits<Iterator>::difference_type test_dt;
typedef typename boost::detail::iterator_traits<Iterator>::iterator_category test_cat;
BOOST_STATIC_ASSERT(( BOOST_STATIC_ASSERT((
boost::is_same< ::boost::is_same<
typename boost::detail::iterator_traits<Iterator>::difference_type, test_dt,
difference_type difference_type
>::value)); >::value));
BOOST_STATIC_ASSERT(( BOOST_STATIC_ASSERT((
boost::is_same< ::boost::is_same<
typename boost::detail::iterator_traits<Iterator>::iterator_category, test_cat,
category category
>::value)); >::value));
}; };
@@ -121,9 +125,10 @@ template <class Iterator,
struct input_iterator_test struct input_iterator_test
: portable_tests<Iterator,value_type,difference_type,pointer,reference,category> : portable_tests<Iterator,value_type,difference_type,pointer,reference,category>
{ {
typedef typename boost::detail::iterator_traits<Iterator>::value_type test_vt;
BOOST_STATIC_ASSERT(( BOOST_STATIC_ASSERT((
boost::is_same< ::boost::is_same<
typename boost::detail::iterator_traits<Iterator>::value_type, test_vt,
value_type value_type
>::value)); >::value));
}; };

View File

@@ -100,7 +100,8 @@ public:
private: private:
// Test data // Test data
static iter_type const fruit_begin, fruit_end; static iter_type const fruit_begin;
static iter_type const fruit_end;
// Test parts // Test parts
static void post_increment_test(); static void post_increment_test();
@@ -123,12 +124,12 @@ test_opr_base::scratch_array_type
test_opr_base::scratch = ""; test_opr_base::scratch = "";
template <typename T, typename R, typename P> template <typename T, typename R, typename P>
typename test_opr<T, R, P>::iter_type const typename test_opr<T, R, P>::iter_type const
test_opr<T, R, P>::fruit_begin( fruit ); test_opr<T, R, P>::fruit_begin = test_iter<T,R,P>( fruit );
template <typename T, typename R, typename P> template <typename T, typename R, typename P>
typename test_opr<T, R, P>::iter_type const typename test_opr<T, R, P>::iter_type const
test_opr<T, R, P>::fruit_end( fruit + fruit_length ); test_opr<T, R, P>::fruit_end = test_iter<T,R,P>( fruit + fruit_length );
// Main testing function // Main testing function

View File

@@ -20,7 +20,7 @@
namespace namespace
{ {
class DontTreadOnMe : boost::noncopyable class DontTreadOnMe : private boost::noncopyable
{ {
public: public:
DontTreadOnMe() { std::cout << "defanged!" << std::endl; } DontTreadOnMe() { std::cout << "defanged!" << std::endl; }

View File

@@ -347,7 +347,7 @@ void test(Number* = 0)
// factoring out difference_type for the assert below confused Borland :( // factoring out difference_type for the assert below confused Borland :(
typedef boost::detail::is_signed< typedef boost::detail::is_signed<
#ifndef BOOST_MSVC #if !defined(BOOST_MSVC) || BOOST_MSVC > 1300
typename typename
#endif #endif
boost::detail::numeric_traits<Number>::difference_type boost::detail::numeric_traits<Number>::difference_type

View File

@@ -499,7 +499,6 @@ namespace
void operator()(boost::minstd_rand& randomizer) const void operator()(boost::minstd_rand& randomizer) const
{ {
Big b1 = Big( randomizer() ); Big b1 = Big( randomizer() );
Big b2 = Big( randomizer() );
Small s = Small( randomizer() ); Small s = Small( randomizer() );
test_left( Wrapped6<Big, Small>(b1), s, b1, s ); test_left( Wrapped6<Big, Small>(b1), s, b1, s );

View File

@@ -47,7 +47,7 @@ namespace boost {
<p>The <code>permutation_iterator_generator</code> is a helper class whose purpose <p>The <code>permutation_iterator_generator</code> is a helper class whose purpose
is to construct a permutation iterator <strong>type</strong>. This class has is to construct a permutation iterator <strong>type</strong>. This class has
two template arguments, the first being the iterator type over the range V, the two template arguments, the first being the iterator type over the range V, the
second being the type of iterator over the indices. second being the type of the iterator over the indices.
<blockquote> <blockquote>
<pre> <pre>
@@ -78,9 +78,9 @@ of <a href="http://www.sgi.com/tech/stl/RandomAccessIterator.html">RandomAccessI
<tr> <tr>
<td><tt>IndexIterator</tt></td> <td><tt>IndexIterator</tt></td>
<td>The iterator over the new indexing scheme. This type must at least be a model <td>The iterator over the new indexing scheme. This type must at least be a model
of <a href="http://www.sgi.com/tech/stl/ForwardIterator.html">ForwardIterator</a></td>. of <a href="http://www.sgi.com/tech/stl/ForwardIterator.html">ForwardIterator</a>.
The <code>IndexIterator::value_type</code> must be convertible to the The <code>IndexIterator::value_type</code> must be convertible to the
<code>ElementIterator::difference_type</code>. <code>ElementIterator::difference_type</code>.</td>
</table> </table>
<h3>Concept Model</h3> <h3>Concept Model</h3>
@@ -91,9 +91,9 @@ The permutation iterator implements the member functions
and operators required for the and operators required for the
<a href="http://www.sgi.com/tech/stl/RandomAccessIterator.html">Random Access Iterator</a> <a href="http://www.sgi.com/tech/stl/RandomAccessIterator.html">Random Access Iterator</a>
concept. However, the permutation iterator can only meet the complexity guarantees concept. However, the permutation iterator can only meet the complexity guarantees
of the same concept as the OrderIterator. Thus for instance, although the permutation of the same concept as the IndexIterator. Thus for instance, although the permutation
iterator provides <code>operator+=(distance)</code>, this operation will take linear time iterator provides <code>operator+=(distance)</code>, this operation will take linear time
in case the OrderIterator is a model of ForwardIterator instead of amortized constant time. in case the IndexIterator is a model of ForwardIterator instead of amortized constant time.
<br> <br>
@@ -108,13 +108,16 @@ types.
<pre> <pre>
template &lt;class ElementIterator, class IndexIterator &gt; template &lt;class ElementIterator, class IndexIterator &gt;
typename permutation_iterator_generator&lt;ElementIterator, IndexIterator&gt;::type typename permutation_iterator_generator&lt;ElementIterator, IndexIterator&gt;::type
make_permutation_iterator(ElementIterator&amp; base, IndexIterator&amp; order); make_permutation_iterator(ElementIterator&amp; base, IndexIterator&amp; indices);
</pre> </pre>
</blockquote> </blockquote>
<h2>Example</h2> <h2>Example</h2>
<blockquote> <blockquote>
<pre> <pre>
using namespace boost;
int i = 0;
typedef std::vector< int > element_range_type; typedef std::vector< int > element_range_type;
typedef std::list< int > index_type; typedef std::list< int > index_type;
@@ -122,10 +125,10 @@ make_permutation_iterator(ElementIterator&amp; base, IndexIterator&amp; order);
static const int index_size = 4; static const int index_size = 4;
element_range_type elements( element_range_size ); element_range_type elements( element_range_size );
std::iota( elements.begin(), elements.end(), 0 ); for(element_range_type::iterator el_it = elements.begin() ; el_it != elements.end() ; ++el_it) *el_it = std::distance(elements.begin(), el_it);
index_type indices( index_size ); index_type indices( index_size );
std::iota( indices.begin(), indices.end(), element_range_size - index_size ); for(index_type::iterator i_it = indices.begin() ; i_it != indices.end() ; ++i_it ) *i_it = element_range_size - index_size + std::distance(indices.begin(), i_it);
std::reverse( indices.begin(), indices.end() ); std::reverse( indices.begin(), indices.end() );
typedef permutation_iterator_generator< element_range_type::iterator, index_type::iterator >::type permutation_type; typedef permutation_iterator_generator< element_range_type::iterator, index_type::iterator >::type permutation_type;
@@ -133,18 +136,33 @@ make_permutation_iterator(ElementIterator&amp; base, IndexIterator&amp; order);
permutation_type it = begin; permutation_type it = begin;
permutation_type end = make_permutation_iterator( elements.begin(), indices.end() ); permutation_type end = make_permutation_iterator( elements.begin(), indices.end() );
std::cout.setf( std::ios_base::left ); std::cout << "The original range is : ";
std::cout << std::setw( 50 ) << "The original range is : ";
std::copy( elements.begin(), elements.end(), std::ostream_iterator< int >( std::cout, " " ) ); std::copy( elements.begin(), elements.end(), std::ostream_iterator< int >( std::cout, " " ) );
std::cout << "\n"; std::cout << "\n";
std::cout << std::setw( 50 ) << "The reindexing scheme is : "; std::cout << "The reindexing scheme is : ";
std::copy( indices.begin(), indices.end(), std::ostream_iterator< int >( std::cout, " " ) ); std::copy( indices.begin(), indices.end(), std::ostream_iterator< int >( std::cout, " " ) );
std::cout << "\n"; std::cout << "\n";
std::cout << std::setw( 50 ) << "The permutated range is : "; std::cout << "The permutated range is : ";
std::copy( begin, end, std::ostream_iterator< int >( std::cout, " " ) ); std::copy( begin, end, std::ostream_iterator< int >( std::cout, " " ) );
std::cout << "\n"; std::cout << "\n";
std::cout << "Elements at even indices in the permutation : ";
it = begin;
for(i = 0; i < index_size / 2 ; ++i, it+=2 ) std::cout << *it << " ";
std::cout << "\n";
std::cout << "Permutation backwards : ";
it = begin + (index_size);
assert( it != begin );
for( ; it-- != begin ; ) std::cout << *it << " ";
std::cout << "\n";
std::cout << "Iterate backward with stride 2 : ";
it = begin + (index_size - 1);
for(i = 0 ; i < index_size / 2 ; ++i, it-=2 ) std::cout << *it << " ";
std::cout << "\n";
</pre> </pre>
</blockquote> </blockquote>

115
ref_ct_test.cpp Normal file
View File

@@ -0,0 +1,115 @@
// compile-time test for "boost/ref.hpp" header content
// see 'ref_test.cpp' for run-time part
#include <boost/ref.hpp>
#include <boost/type_traits/same_traits.hpp>
#include <boost/static_assert.hpp>
namespace {
template< typename T, typename U >
void ref_test(boost::reference_wrapper<U>)
{
typedef typename boost::reference_wrapper<U>::type type;
BOOST_STATIC_ASSERT((boost::is_same<U,type>::value));
BOOST_STATIC_ASSERT((boost::is_same<T,type>::value));
}
template< typename T >
void assignable_test(T x)
{
x = x;
}
template< bool R, typename T >
void is_reference_wrapper_test(T)
{
BOOST_STATIC_ASSERT(boost::is_reference_wrapper<T>::value == R);
}
template< typename R, typename Ref >
void cxx_reference_test(Ref)
{
BOOST_STATIC_ASSERT((boost::is_same<R,Ref>::value));
}
template< typename R, typename Ref >
void unwrap_reference_test(Ref)
{
typedef typename boost::unwrap_reference<Ref>::type type;
BOOST_STATIC_ASSERT((boost::is_same<R,type>::value));
}
} // namespace
int main()
{
int i = 0;
int& ri = i;
int const ci = 0;
int const& rci = ci;
// 'ref/cref' functions test
ref_test<int>(boost::ref(i));
ref_test<int>(boost::ref(ri));
ref_test<int const>(boost::ref(ci));
ref_test<int const>(boost::ref(rci));
ref_test<int const>(boost::cref(i));
ref_test<int const>(boost::cref(ri));
ref_test<int const>(boost::cref(ci));
ref_test<int const>(boost::cref(rci));
// test 'assignable' requirement
assignable_test(boost::ref(i));
assignable_test(boost::ref(ri));
assignable_test(boost::cref(i));
assignable_test(boost::cref(ci));
assignable_test(boost::cref(rci));
// 'is_reference_wrapper' test
is_reference_wrapper_test<true>(boost::ref(i));
is_reference_wrapper_test<true>(boost::ref(ri));
is_reference_wrapper_test<true>(boost::cref(i));
is_reference_wrapper_test<true>(boost::cref(ci));
is_reference_wrapper_test<true>(boost::cref(rci));
is_reference_wrapper_test<false>(i);
is_reference_wrapper_test<false, int&>(ri);
is_reference_wrapper_test<false>(ci);
is_reference_wrapper_test<false, int const&>(rci);
// ordinary references/function template arguments deduction test
cxx_reference_test<int>(i);
cxx_reference_test<int>(ri);
cxx_reference_test<int>(ci);
cxx_reference_test<int>(rci);
cxx_reference_test<int&, int&>(i);
cxx_reference_test<int&, int&>(ri);
cxx_reference_test<int const&, int const&>(i);
cxx_reference_test<int const&, int const&>(ri);
cxx_reference_test<int const&, int const&>(ci);
cxx_reference_test<int const&, int const&>(rci);
// 'unwrap_reference' test
unwrap_reference_test<int>(boost::ref(i));
unwrap_reference_test<int>(boost::ref(ri));
unwrap_reference_test<int const>(boost::cref(i));
unwrap_reference_test<int const>(boost::cref(ci));
unwrap_reference_test<int const>(boost::cref(rci));
unwrap_reference_test<int>(i);
unwrap_reference_test<int>(ri);
unwrap_reference_test<int>(ci);
unwrap_reference_test<int>(rci);
unwrap_reference_test<int&, int&>(i);
unwrap_reference_test<int&, int&>(ri);
unwrap_reference_test<int const&, int const&>(i);
unwrap_reference_test<int const&, int const&>(ri);
unwrap_reference_test<int const&, int const&>(ci);
unwrap_reference_test<int const&, int const&>(rci);
return 0;
}

74
ref_test.cpp Normal file
View File

@@ -0,0 +1,74 @@
// run-time test for "boost/ref.hpp" header content
// see 'ref_ct_test.cpp' for compile-time part
#if defined(_MSC_VER) && !defined(__ICL)
# pragma warning(disable: 4786) // identifier truncated in debug info
# pragma warning(disable: 4710) // function not inlined
# pragma warning(disable: 4711) // function selected for automatic inline expansion
# pragma warning(disable: 4514) // unreferenced inline removed
#endif
#include <boost/ref.hpp>
#if defined(BOOST_MSVC) && (BOOST_MSVC < 1300)
# pragma warning(push, 3)
#endif
#include <iostream>
#if defined(BOOST_MSVC) && (BOOST_MSVC < 1300)
# pragma warning(pop)
#endif
#define BOOST_INCLUDE_MAIN
#include <boost/test/test_tools.hpp>
namespace {
using namespace boost;
template <class T>
struct ref_wrapper
{
// Used to verify implicit conversion
static T* get_pointer(T& x)
{
return &x;
}
static T const* get_const_pointer(T const& x)
{
return &x;
}
template <class Arg>
static T* passthru(Arg x)
{
return get_pointer(x);
}
template <class Arg>
static T const* cref_passthru(Arg x)
{
return get_const_pointer(x);
}
static void test(T x)
{
BOOST_TEST(passthru(ref(x)) == &x);
BOOST_TEST(&ref(x).get() == &x);
BOOST_TEST(cref_passthru(cref(x)) == &x);
BOOST_TEST(&cref(x).get() == &x);
}
};
} // namespace unnamed
int test_main(int, char * [])
{
ref_wrapper<int>::test(1);
ref_wrapper<int const>::test(1);
return 0;
}

View File

@@ -10,17 +10,26 @@
int main(int, char*[]) int main(int, char*[])
{ {
char letters[] = "hello world!"; char letters_[] = "hello world!";
const int N = sizeof(letters)/sizeof(char) - 1; const int N = sizeof(letters_)/sizeof(char) - 1;
#ifdef BOOST_NO_STD_ITERATOR_TRAITS
// Assume there won't be proper iterator traits for pointers. This
// is just a wrapper for char* which has the right traits.
typedef boost::iterator_adaptor<char*, boost::default_iterator_policies, char> base_iterator;
#else
typedef char* base_iterator;
#endif
base_iterator letters(letters_);
std::cout << "original sequence of letters:\t" std::cout << "original sequence of letters:\t"
<< letters << std::endl; << letters_ << std::endl;
std::sort(letters, letters + N); std::sort(letters, letters + N);
// Use reverse_iterator_generator to print a sequence // Use reverse_iterator_generator to print a sequence
// of letters in reverse order. // of letters in reverse order.
boost::reverse_iterator_generator<char*>::type boost::reverse_iterator_generator<base_iterator>::type
reverse_letters_first(letters + N), reverse_letters_first(letters + N),
reverse_letters_last(letters); reverse_letters_last(letters);

View File

@@ -19,6 +19,7 @@
#include <set> #include <set>
#include <algorithm> #include <algorithm>
#include <iostream> #include <iostream>
#include <iterator> // std::distance
// Note: tie() use to live in boost/utility.hpp, but // Note: tie() use to live in boost/utility.hpp, but
// not it is part of the more general Boost Tuple Library. // not it is part of the more general Boost Tuple Library.
#include <boost/tuple/tuple.hpp> #include <boost/tuple/tuple.hpp>

View File

@@ -22,6 +22,7 @@
checked_array_delete()</a></li> checked_array_delete()</a></li>
<li>Function templates <a href="#functions next">next() and prior()</a></li> <li>Function templates <a href="#functions next">next() and prior()</a></li>
<li>Class <a href="#Class noncopyable">noncopyable</a></li> <li>Class <a href="#Class noncopyable">noncopyable</a></li>
<li>Function template <a href="#addressof">addressof()</a></li>
<li>Function template <a href="tie.html">tie()</a> and supporting class tied.</li> <li>Function template <a href="tie.html">tie()</a> and supporting class tied.</li>
</ul> </ul>
<h2> Function templates <a name="checked_delete">checked_delete</a>() and <h2> Function templates <a name="checked_delete">checked_delete</a>() and
@@ -133,6 +134,48 @@ emphasize that it is to be used only as a base class.&nbsp; Dave Abrahams notes
concern about the effect on compiler optimization of adding (even trivial inline) concern about the effect on compiler optimization of adding (even trivial inline)
destructor declarations. He says &quot;Probably this concern is misplaced, because destructor declarations. He says &quot;Probably this concern is misplaced, because
noncopyable will be used mostly for classes which own resources and thus have non-trivial destruction semantics.&quot;</p> noncopyable will be used mostly for classes which own resources and thus have non-trivial destruction semantics.&quot;</p>
<h2><a name="addressof">Function template addressof()</a></h2>
<p>Function <strong>addressof()</strong> returns the address of an object.</p>
<blockquote>
<pre>
template &lt;typename T&gt; inline T* addressof(T& v);
template &lt;typename T&gt; inline const T* addressof(const T& v);
template &lt;typename T&gt; inline volatile T* addressof(volatile T& v);
template &lt;typename T&gt; inline const volatile T* addressof(const volatile T& v);
</pre>
</blockquote>
<p>C++ allows programmers to replace the unary
<strong>operator&()</strong> class member used to get the address of
an object. Getting the real address of an object requires ugly
casting tricks to avoid invoking the overloaded
<strong>operator&()</strong>. Function <strong>addressof()</strong>
provides a wrapper around the necessary code to make it easy to get an
object's real address.
</p>
<p>The program <a href="addressof_test.cpp">addressof_test.cpp</a> can be
used to verify that <b>addressof()</b> works as expected.</p>
<p>Contributed by Brad King based on ideas from discussion with Doug Gregor.</p>
<h3>Example</h3>
<blockquote>
<pre>#include &lt;boost/utility.hpp&gt;
struct useless_type {};
class nonaddressable {
useless_type operator&() const;
};
void f() {
nonaddressable x;
nonaddressable* xp = boost::addressof(x);
// nonaddressable* xpe = &amp;x; /* error */
}</pre>
</blockquote>
<h2>Class templates for the Base-from-Member Idiom</h2> <h2>Class templates for the Base-from-Member Idiom</h2>
<p>See <a href="base_from_member.html">separate documentation</a>.</p> <p>See <a href="base_from_member.html">separate documentation</a>.</p>
<h2>Function template tie()</h2> <h2>Function template tie()</h2>