forked from boostorg/iterator
Compare commits
524 Commits
svn-branch
...
svn-branch
Author | SHA1 | Date | |
---|---|---|---|
ae90264865 | |||
bf7d904bf8 | |||
efecbd0d27 | |||
65e229fb0d | |||
bd5731efa9 | |||
a2d9e63f94 | |||
f34109aa26 | |||
0f88de3d88 | |||
107595b76c | |||
1f0a885def | |||
5bf5110cdb | |||
0b095e687f | |||
c0d6dacf62 | |||
c080ee4dcf | |||
9d241238f8 | |||
45f64ea8f7 | |||
71abf15b60 | |||
7243852b0a | |||
e7843bdea3 | |||
bca372da18 | |||
0237e49a17 | |||
b5492bd866 | |||
1fad13e34f | |||
3355660636 | |||
eaf9bf62d1 | |||
9f20320f59 | |||
2cb253ed35 | |||
230d47e93a | |||
e2957cfb0c | |||
f5b644e765 | |||
28dd458088 | |||
0dbe767eec | |||
c0fc8532e7 | |||
a4e7ba6c28 | |||
58341b3517 | |||
e23a647cff | |||
d801e64289 | |||
f5a31849f0 | |||
7846e4bfd7 | |||
6368d38802 | |||
6a79b6014b | |||
73811245eb | |||
1c3e6c5b65 | |||
ae10a3b706 | |||
48f7be7015 | |||
bbef2422ad | |||
ae45f7abf7 | |||
6363297754 | |||
55fd9078a1 | |||
e22bb495db | |||
54ae365c98 | |||
a9483b5633 | |||
65fe75e558 | |||
7a43350655 | |||
df49ae74e0 | |||
3fe9b7517e | |||
ab372a0a74 | |||
f9c4915b55 | |||
741da59c0d | |||
a0b28e4c8b | |||
ef895f0cc7 | |||
1d018cc602 | |||
88697aad65 | |||
7344357e32 | |||
80501e1eb2 | |||
7707262a07 | |||
ba3e7a459e | |||
295ae05e40 | |||
68268f81eb | |||
3b60f75bc6 | |||
a8f528130a | |||
c0788f2cd8 | |||
c6bc3b2547 | |||
27adbbb6ed | |||
1f999864a1 | |||
65af4c96a9 | |||
aa9e49b727 | |||
3318c82f83 | |||
68791c337a | |||
a396085bc0 | |||
6196a6e591 | |||
4e07575b78 | |||
557ef60557 | |||
4b583d3aa0 | |||
3eca5e8f60 | |||
5947d569b9 | |||
e469abbf57 | |||
c141f6cc59 | |||
55f8a6380a | |||
9c955e8af2 | |||
82108581b9 | |||
c4834d363e | |||
7194aff64c | |||
ca41a4f902 | |||
47a3392c80 | |||
bd765a21fb | |||
cad110e0f3 | |||
3599398eca | |||
dd72d599c8 | |||
1a9677d9dc | |||
a6d200f262 | |||
0c28649d0b | |||
d6405ddd54 | |||
700db48ac7 | |||
2241bb1ae3 | |||
539add7de6 | |||
edb7528136 | |||
254186d6bd | |||
aa62f4f9c7 | |||
f0bc339d55 | |||
2721c3c97e | |||
f49f68c8fe | |||
02f606816d | |||
1ffc31cc37 | |||
0acc6c38ef | |||
da1e5aa3e8 | |||
db0bc36f58 | |||
99bafe363c | |||
b310ccda97 | |||
2a9c00f5b2 | |||
020d0b8f99 | |||
d21781d8d1 | |||
bed1d7fa7a | |||
0c3a68530e | |||
d3daa47561 | |||
62c993978a | |||
74f41dcb5b | |||
c8d1461340 | |||
13dcd5590f | |||
7f125cacb9 | |||
8cf04e1c7b | |||
0122a0c8ec | |||
09549783cc | |||
273c1d784c | |||
a99ab81803 | |||
0cb4ce54ef | |||
0670e05297 | |||
b353d45f2d | |||
19d339c916 | |||
506517191c | |||
b502873f00 | |||
b838d27aa3 | |||
17c373ded3 | |||
09e1cb9a38 | |||
58288cfb48 | |||
cd730895ca | |||
2d2a84f8c4 | |||
4871736269 | |||
fec82e2de8 | |||
a5b14e1a4f | |||
8480d452a9 | |||
5f870d780d | |||
010f715950 | |||
020f2ab867 | |||
2071230859 | |||
413d0b01cf | |||
4abd97910d | |||
564ed3ed88 | |||
c90814e515 | |||
576395a469 | |||
f75a60e074 | |||
3e5f366f4f | |||
a456f8d969 | |||
cfe17e7fe5 | |||
99891db75c | |||
287c7ed0e7 | |||
8bd881070c | |||
9cce6e8052 | |||
b6068667c9 | |||
309f741588 | |||
858e0e0c0b | |||
01fd0c92e3 | |||
23dcc53fed | |||
08cd7bf6e7 | |||
35c14adc12 | |||
3b992521af | |||
646e78dc14 | |||
4a7f6afd6a | |||
8294e14664 | |||
1102c88de7 | |||
c98620a552 | |||
24fcaed649 | |||
2c1eadfea3 | |||
ffe87e904f | |||
fbd5da7237 | |||
ecccc89a70 | |||
2bacc663b1 | |||
c5dc0fbf0e | |||
f358cf3bf4 | |||
6b00e8e0ca | |||
5abf4d7556 | |||
8ca421c140 | |||
1e3da4b77f | |||
7c784ad112 | |||
f72d264b6b | |||
c6526fc609 | |||
3741fa77d2 | |||
ca70d5dee8 | |||
85ad1f59da | |||
73e6736566 | |||
c08cc33394 | |||
8c3ed628dc | |||
792acdb408 | |||
c3fd7076c1 | |||
33f630beca | |||
f1f6262be7 | |||
42147b9e86 | |||
2854c5c761 | |||
731576fbfe | |||
36329b053d | |||
3b93bb25ff | |||
2496402a8c | |||
8a0e9a4fe5 | |||
5049bcdce5 | |||
1c77a5a4ab | |||
9c42ccb0bd | |||
dd50d3f2ab | |||
5f3b97ceff | |||
2d1e40bd20 | |||
a0bb423311 | |||
0f8c236e9d | |||
736044938d | |||
983ba32def | |||
d2dae62215 | |||
9540444061 | |||
482c0cf52b | |||
849f01a0d1 | |||
11770763df | |||
df66940f0f | |||
80f6a13e79 | |||
0f8aa07e5c | |||
6b77e7f8bd | |||
838decca95 | |||
e6c5b80afd | |||
e7b5604ec5 | |||
ea3baba376 | |||
c6a5b7c292 | |||
45e90e0134 | |||
18b1414d6c | |||
7facdd8590 | |||
6cf1230c13 | |||
d70b0d3f05 | |||
527b5e3caa | |||
4e1b53ed36 | |||
eb69638be1 | |||
a5c4497c01 | |||
1033aeb186 | |||
e5d502d2f8 | |||
55e4fe2ab7 | |||
8e2d210d42 | |||
ec8d069057 | |||
2edb688882 | |||
3403cbbae6 | |||
b52b9325ba | |||
1e3b131a84 | |||
250a374e07 | |||
f618d71c0e | |||
3d37ba5120 | |||
e785cc70d1 | |||
3bf52ec2f2 | |||
19dbb5304c | |||
4d13c285ea | |||
08ce6903ce | |||
75e76eb637 | |||
954d12a04d | |||
bcc0e80439 | |||
436f7411f8 | |||
21381f3fa7 | |||
db9d88ad7b | |||
6085e03da0 | |||
b2407b0191 | |||
8181625365 | |||
24052c3dff | |||
c15707fd70 | |||
b4f1b069be | |||
129815f3dd | |||
a7eaa017b1 | |||
6e326921f9 | |||
4a3fd9984d | |||
0074f50573 | |||
ba8dc44eac | |||
b0d3d34fcd | |||
7f0ed4f5be | |||
7fc54ec2d8 | |||
f0add8a043 | |||
5b608e114b | |||
06e1fa88b9 | |||
a6b2a098c1 | |||
4f0684ffac | |||
fbfcf97e18 | |||
45b6a92f61 | |||
c6814925ac | |||
6c114a539d | |||
b6c82968b8 | |||
2271aceab8 | |||
0db07e9455 | |||
f158591054 | |||
1b210355bf | |||
075c341a37 | |||
bab25c04db | |||
2a60dfa087 | |||
ef69c73e89 | |||
bf9534e1ee | |||
0e11bd6a0c | |||
ff10cfd5dc | |||
400f35cbb0 | |||
59340bca4c | |||
6c62f31f0a | |||
dd5fb425fa | |||
c903cf4801 | |||
1c26f7dd43 | |||
c546a3e875 | |||
2183de96a1 | |||
fb1fc6f909 | |||
20b31d1cca | |||
f716d705c5 | |||
1fca93be10 | |||
f96a2b3d81 | |||
a7edd713d8 | |||
bca1c2dea5 | |||
dfad37d0f9 | |||
3376955b80 | |||
e98b130d77 | |||
a450053b0a | |||
0b5b315a7f | |||
5cc31f6539 | |||
f0248daa1e | |||
798562e75b | |||
68e7d3f0d5 | |||
e9bb297ed2 | |||
d5e525dd19 | |||
c326818764 | |||
57ec457f32 | |||
c04b13641f | |||
0bf570c98d | |||
28dfcbd6b0 | |||
9338b11799 | |||
ad5defc9af | |||
81242ad5ae | |||
8997a587e9 | |||
83de27a445 | |||
44d7dfeb9b | |||
84f22cde8d | |||
9387c05d12 | |||
66feb45676 | |||
bdbfcd308e | |||
44757cfcc1 | |||
c1be620888 | |||
36d9a73a60 | |||
f14701232a | |||
296ce3aa89 | |||
1f7c08615f | |||
1b29ec1741 | |||
593311f43e | |||
fe52e0d665 | |||
52e34b2e26 | |||
8cfa950f10 | |||
cc282d81c0 | |||
8c01469b3c | |||
a6ffdb8ebf | |||
2ad29da3b5 | |||
459387273b | |||
09ea8d27e2 | |||
ca1ee306b7 | |||
b63814d3f2 | |||
dfc09c4b26 | |||
f6715137cf | |||
f18906ac6b | |||
522195fd64 | |||
bdc1304326 | |||
633bb0762e | |||
b0b5699a01 | |||
943d2c872b | |||
4ec68b7a0e | |||
e295f71a85 | |||
a8a68dbb7b | |||
8d5717081e | |||
76880f6ce2 | |||
50e645261c | |||
f25ff7a1a4 | |||
104faa5ab3 | |||
4cc5f9a4d6 | |||
7946d32cef | |||
69d8856572 | |||
c055f1afae | |||
cb34b65f3f | |||
f8cd96cb2e | |||
fed5967d9d | |||
81870ac8b6 | |||
6ef3e5d1c7 | |||
dfa751077a | |||
14134e4610 | |||
c7bec1cf56 | |||
e888f18b5a | |||
15abd4c56e | |||
17026cc30d | |||
1c39976ccd | |||
361f62d022 | |||
ebb09db44e | |||
50fe1b062b | |||
30ca43dd08 | |||
ac0c6461fb | |||
d85b8db0aa | |||
a3856b5c60 | |||
20e2818844 | |||
d68ac3db4c | |||
5efcabf3bd | |||
9ac583096c | |||
1710c484b3 | |||
f6cbffeda0 | |||
50ab635593 | |||
d958a5bc82 | |||
5339d7a9d4 | |||
fd29e538ed | |||
1c41a7d0ec | |||
85873e924a | |||
d9b4e41d5a | |||
4968b50fc2 | |||
cbeb7f0632 | |||
abf8390020 | |||
2c89e2b15a | |||
3f49409843 | |||
abafc5d1be | |||
2b7ed5f7a8 | |||
f801c39a59 | |||
bb7ac6bd84 | |||
f325582c40 | |||
36feca8a52 | |||
a5179f6dfc | |||
f98f3497b8 | |||
76af84c0e7 | |||
0f42b93c3b | |||
19977c757f | |||
508696a169 | |||
3ab9da6a99 | |||
bd3312cdf2 | |||
87f93ec521 | |||
afa92675a2 | |||
ed8c60c20b | |||
3fe0d4b532 | |||
8a51271e3b | |||
52c0d22cff | |||
e4447b8e83 | |||
42e873e10c | |||
57a40c8cd2 | |||
a982c42303 | |||
9db269bb5b | |||
e5eaaf6a55 | |||
2225787093 | |||
f19c1c4059 | |||
b0aef5a66d | |||
dfc43d81cf | |||
eda969d7b5 | |||
4c8415a99f | |||
1d6f36e35d | |||
04301ac6e9 | |||
a1ec9da737 | |||
e2a47bdbe5 | |||
2b1fc22b61 | |||
273ec4b975 | |||
4716891117 | |||
80d9e8e4c1 | |||
53eb5346de | |||
e28ca345ea | |||
92d461cda1 | |||
8dace06f04 | |||
ef0bff57d3 | |||
5bacd289b6 | |||
77c1698c6e | |||
2c302ee549 | |||
a586f20d19 | |||
34c159dd8d | |||
b22a3adc02 | |||
4a24e0f401 | |||
3844edc4bf | |||
fdd1601ba4 | |||
e9b33b336c | |||
2574365b5c | |||
12b9366f33 | |||
4772bb099e | |||
2be5179020 | |||
8cb49713b4 | |||
bd666dc0e9 | |||
57251d58cc | |||
ebcb4d861a | |||
15a7a839f9 | |||
76a307d31e | |||
37aee7c13b | |||
50a502bb81 | |||
8a4839354e | |||
4da7371246 | |||
e162a75e53 | |||
e60df6ad92 | |||
4c2b3a9d2c | |||
75023a1dd3 | |||
79370a6dfb | |||
4566798afc | |||
3fd1c4bc5d | |||
2d6f48d5ab | |||
d1c7594344 | |||
ac327f51e9 | |||
4e18b11263 | |||
81e3df2b36 | |||
ac05307515 | |||
552a1e6785 | |||
134b8b51aa | |||
efecfd17b9 | |||
799158841e | |||
582ebfd054 | |||
42e4db1539 | |||
d7023154a3 | |||
9582b2223c | |||
d7908fb81f | |||
e48cdcb94f | |||
0846ad5fd0 | |||
84663ff2e2 | |||
6de1934420 | |||
a110b9fd27 | |||
eb06c122d1 | |||
cbbe851adb | |||
f6cc2e520f | |||
4e29b5aa29 | |||
d924f56ad8 | |||
f27fd095f7 |
@ -1,282 +0,0 @@
|
|||||||
#ifndef BOOST_ITERATOR_CONCEPTS_HPP
|
|
||||||
#define BOOST_ITERATOR_CONCEPTS_HPP
|
|
||||||
|
|
||||||
#include <boost/concept_check.hpp>
|
|
||||||
#include <boost/iterator_traits.hpp>
|
|
||||||
|
|
||||||
namespace boost_concepts {
|
|
||||||
// Used a different namespace here (instead of "boost") so that the
|
|
||||||
// concept descriptions do not take for granted the names in
|
|
||||||
// namespace boost.
|
|
||||||
|
|
||||||
|
|
||||||
//===========================================================================
|
|
||||||
|
|
||||||
template <typename Iterator>
|
|
||||||
class ReadableIteratorConcept {
|
|
||||||
public:
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::value_type value_type;
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::reference reference;
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::return_category
|
|
||||||
return_category;
|
|
||||||
|
|
||||||
void constraints() {
|
|
||||||
boost::function_requires< boost::SGIAssignableConcept<Iterator> >();
|
|
||||||
boost::function_requires< boost::EqualityComparableConcept<Iterator> >();
|
|
||||||
boost::function_requires< boost::DefaultConstructibleConcept<Iterator> >();
|
|
||||||
|
|
||||||
boost::function_requires<
|
|
||||||
boost::ConvertibleConcept<return_category, boost::readable_iterator_tag> >();
|
|
||||||
|
|
||||||
reference r = *i; // or perhaps read(x)
|
|
||||||
value_type v(r);
|
|
||||||
boost::ignore_unused_variable_warning(v);
|
|
||||||
}
|
|
||||||
Iterator i;
|
|
||||||
};
|
|
||||||
|
|
||||||
template <typename Iterator, typename ValueType>
|
|
||||||
class WritableIteratorConcept {
|
|
||||||
public:
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::return_category
|
|
||||||
return_category;
|
|
||||||
|
|
||||||
void constraints() {
|
|
||||||
boost::function_requires< boost::SGIAssignableConcept<Iterator> >();
|
|
||||||
boost::function_requires< boost::EqualityComparableConcept<Iterator> >();
|
|
||||||
boost::function_requires< boost::DefaultConstructibleConcept<Iterator> >();
|
|
||||||
|
|
||||||
boost::function_requires<
|
|
||||||
boost::ConvertibleConcept<return_category, boost::writable_iterator_tag> >();
|
|
||||||
|
|
||||||
*i = v; // an alternative could be something like write(x, v)
|
|
||||||
}
|
|
||||||
ValueType v;
|
|
||||||
Iterator i;
|
|
||||||
};
|
|
||||||
|
|
||||||
template <typename Iterator>
|
|
||||||
class ConstantLvalueIteratorConcept {
|
|
||||||
public:
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::value_type value_type;
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::reference reference;
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::return_category
|
|
||||||
return_category;
|
|
||||||
|
|
||||||
void constraints() {
|
|
||||||
boost::function_requires< ReadableIteratorConcept<Iterator> >();
|
|
||||||
|
|
||||||
boost::function_requires<
|
|
||||||
boost::ConvertibleConcept<return_category,
|
|
||||||
boost::constant_lvalue_iterator_tag> >();
|
|
||||||
|
|
||||||
typedef typename boost::require_same<reference, const value_type&>::type req;
|
|
||||||
|
|
||||||
reference v = *i;
|
|
||||||
boost::ignore_unused_variable_warning(v);
|
|
||||||
}
|
|
||||||
Iterator i;
|
|
||||||
};
|
|
||||||
|
|
||||||
template <typename Iterator>
|
|
||||||
class MutableLvalueIteratorConcept {
|
|
||||||
public:
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::value_type value_type;
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::reference reference;
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::return_category
|
|
||||||
return_category;
|
|
||||||
|
|
||||||
void constraints() {
|
|
||||||
boost::function_requires< ReadableIteratorConcept<Iterator> >();
|
|
||||||
boost::function_requires< WritableIteratorConcept<Iterator, value_type> >();
|
|
||||||
|
|
||||||
boost::function_requires<
|
|
||||||
boost::ConvertibleConcept<return_category,
|
|
||||||
boost::constant_lvalue_iterator_tag> >();
|
|
||||||
|
|
||||||
typedef typename boost::require_same<reference, value_type&>::type req;
|
|
||||||
|
|
||||||
reference v = *i;
|
|
||||||
boost::ignore_unused_variable_warning(v);
|
|
||||||
}
|
|
||||||
Iterator i;
|
|
||||||
};
|
|
||||||
|
|
||||||
//===========================================================================
|
|
||||||
|
|
||||||
template <typename Iterator>
|
|
||||||
class SinglePassIteratorConcept {
|
|
||||||
public:
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::motion_category
|
|
||||||
motion_category;
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::difference_type
|
|
||||||
difference_type;
|
|
||||||
|
|
||||||
void constraints() {
|
|
||||||
boost::function_requires< boost::SGIAssignableConcept<Iterator> >();
|
|
||||||
boost::function_requires< boost::EqualityComparableConcept<Iterator> >();
|
|
||||||
boost::function_requires< boost::DefaultConstructibleConcept<Iterator> >();
|
|
||||||
|
|
||||||
boost::function_requires<
|
|
||||||
boost::ConvertibleConcept<motion_category,
|
|
||||||
boost::single_pass_iterator_tag> >();
|
|
||||||
|
|
||||||
// difference_type must be a signed integral type
|
|
||||||
|
|
||||||
++i;
|
|
||||||
(void)i++;
|
|
||||||
}
|
|
||||||
|
|
||||||
Iterator i;
|
|
||||||
};
|
|
||||||
|
|
||||||
template <typename Iterator>
|
|
||||||
class ForwardIteratorConcept {
|
|
||||||
public:
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::motion_category
|
|
||||||
motion_category;
|
|
||||||
|
|
||||||
void constraints() {
|
|
||||||
boost::function_requires< SinglePassIteratorConcept<Iterator> >();
|
|
||||||
|
|
||||||
boost::function_requires<
|
|
||||||
boost::ConvertibleConcept<motion_category,
|
|
||||||
boost::forward_iterator_tag> >();
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
template <typename Iterator>
|
|
||||||
class BidirectionalIteratorConcept {
|
|
||||||
public:
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::motion_category
|
|
||||||
motion_category;
|
|
||||||
|
|
||||||
void constraints() {
|
|
||||||
boost::function_requires< ForwardIteratorConcept<Iterator> >();
|
|
||||||
|
|
||||||
boost::function_requires<
|
|
||||||
boost::ConvertibleConcept<motion_category,
|
|
||||||
boost::bidirectional_iterator_tag> >();
|
|
||||||
|
|
||||||
--i;
|
|
||||||
(void)i--;
|
|
||||||
}
|
|
||||||
Iterator i;
|
|
||||||
};
|
|
||||||
|
|
||||||
template <typename Iterator>
|
|
||||||
class RandomAccessIteratorConcept {
|
|
||||||
public:
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::motion_category
|
|
||||||
motion_category;
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::difference_type
|
|
||||||
difference_type;
|
|
||||||
|
|
||||||
void constraints() {
|
|
||||||
boost::function_requires< BidirectionalIteratorConcept<Iterator> >();
|
|
||||||
|
|
||||||
boost::function_requires<
|
|
||||||
boost::ConvertibleConcept<motion_category,
|
|
||||||
boost::random_access_iterator_tag> >();
|
|
||||||
|
|
||||||
i += n;
|
|
||||||
i = i + n;
|
|
||||||
i = n + i;
|
|
||||||
i -= n;
|
|
||||||
i = i - n;
|
|
||||||
n = i - j;
|
|
||||||
}
|
|
||||||
difference_type n;
|
|
||||||
Iterator i, j;
|
|
||||||
};
|
|
||||||
|
|
||||||
//===========================================================================
|
|
||||||
|
|
||||||
template <typename Iterator>
|
|
||||||
class ReadableRandomAccessIteratorConcept {
|
|
||||||
public:
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::value_type value_type;
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::reference reference;
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::difference_type
|
|
||||||
difference_type;
|
|
||||||
|
|
||||||
void constraints() {
|
|
||||||
boost::function_requires< RandomAccessIteratorConcept<Iterator> >();
|
|
||||||
boost::function_requires< ReadableIteratorConcept<Iterator> >();
|
|
||||||
|
|
||||||
reference r = i[n];
|
|
||||||
value_type v(r);
|
|
||||||
boost::ignore_unused_variable_warning(v);
|
|
||||||
}
|
|
||||||
difference_type n;
|
|
||||||
Iterator i;
|
|
||||||
};
|
|
||||||
|
|
||||||
template <typename Iterator>
|
|
||||||
class WritableRandomAccessIteratorConcept {
|
|
||||||
public:
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::value_type value_type;
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::difference_type
|
|
||||||
difference_type;
|
|
||||||
|
|
||||||
void constraints() {
|
|
||||||
boost::function_requires< RandomAccessIteratorConcept<Iterator> >();
|
|
||||||
boost::function_requires< WritableIteratorConcept<Iterator, value_type> >();
|
|
||||||
|
|
||||||
i[n] = v;
|
|
||||||
boost::ignore_unused_variable_warning(v);
|
|
||||||
}
|
|
||||||
difference_type n;
|
|
||||||
value_type v;
|
|
||||||
Iterator i;
|
|
||||||
};
|
|
||||||
|
|
||||||
template <typename Iterator>
|
|
||||||
class ConstantLvalueRandomAccessIteratorConcept {
|
|
||||||
public:
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::value_type value_type;
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::reference reference;
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::difference_type
|
|
||||||
difference_type;
|
|
||||||
|
|
||||||
void constraints() {
|
|
||||||
boost::function_requires< RandomAccessIteratorConcept<Iterator> >();
|
|
||||||
boost::function_requires< ReadableIteratorConcept<Iterator> >();
|
|
||||||
|
|
||||||
typedef typename boost::require_same<reference, const value_type&>::type req;
|
|
||||||
|
|
||||||
reference v = i[n];
|
|
||||||
boost::ignore_unused_variable_warning(v);
|
|
||||||
}
|
|
||||||
difference_type n;
|
|
||||||
value_type v;
|
|
||||||
Iterator i;
|
|
||||||
};
|
|
||||||
|
|
||||||
template <typename Iterator>
|
|
||||||
class MutableLvalueRandomAccessIteratorConcept {
|
|
||||||
public:
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::value_type value_type;
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::reference reference;
|
|
||||||
typedef typename boost::iterator_traits<Iterator>::difference_type
|
|
||||||
difference_type;
|
|
||||||
|
|
||||||
void constraints() {
|
|
||||||
boost::function_requires< RandomAccessIteratorConcept<Iterator> >();
|
|
||||||
boost::function_requires< WritableIteratorConcept<Iterator, value_type> >();
|
|
||||||
boost::function_requires< ReadableIteratorConcept<Iterator> >();
|
|
||||||
|
|
||||||
typedef typename boost::require_same<reference, value_type&>::type req;
|
|
||||||
|
|
||||||
reference v = i[n];
|
|
||||||
boost::ignore_unused_variable_warning(v);
|
|
||||||
}
|
|
||||||
difference_type n;
|
|
||||||
value_type v;
|
|
||||||
Iterator i;
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace boost_concepts
|
|
||||||
|
|
||||||
|
|
||||||
#endif // BOOST_ITERATOR_CONCEPTS_HPP
|
|
@ -1,60 +0,0 @@
|
|||||||
#ifndef BOOST_ITERATOR_TRAITS_HPP
|
|
||||||
#define BOOST_ITERATOR_TRAITS_HPP
|
|
||||||
|
|
||||||
#include <boost/config.hpp>
|
|
||||||
#include <boost/type_traits.hpp>
|
|
||||||
|
|
||||||
namespace boost {
|
|
||||||
|
|
||||||
template <typename Iterator>
|
|
||||||
struct iterator_traits {
|
|
||||||
typedef typename Iterator::value_type value_type;
|
|
||||||
typedef typename Iterator::reference reference;
|
|
||||||
typedef typename Iterator::pointer pointer;
|
|
||||||
typedef typename Iterator::difference_type difference_type;
|
|
||||||
typedef typename Iterator::return_category return_category;
|
|
||||||
typedef typename Iterator::motion_category motion_category;
|
|
||||||
};
|
|
||||||
|
|
||||||
// Motion Categories
|
|
||||||
struct single_pass_iterator_tag { };
|
|
||||||
struct forward_iterator_tag : public single_pass_iterator_tag { };
|
|
||||||
struct bidirectional_iterator_tag : public forward_iterator_tag { };
|
|
||||||
struct random_access_iterator_tag : public bidirectional_iterator_tag { };
|
|
||||||
|
|
||||||
// Return Type Categories
|
|
||||||
struct readable_iterator_tag { };
|
|
||||||
struct writable_iterator_tag { };
|
|
||||||
struct mutable_lvalue_iterator_tag : virtual public writable_iterator_tag,
|
|
||||||
virtual public readable_iterator_tag { };
|
|
||||||
struct constant_lvalue_iterator_tag : public readable_iterator_tag { };
|
|
||||||
|
|
||||||
#if !defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION)
|
|
||||||
|
|
||||||
namespace detail {
|
|
||||||
template <bool IsConst>
|
|
||||||
struct pointer_return_category {
|
|
||||||
typedef constant_lvalue_iterator_tag type;
|
|
||||||
};
|
|
||||||
template <>
|
|
||||||
struct pointer_return_category<false> {
|
|
||||||
typedef mutable_lvalue_iterator_tag type;
|
|
||||||
};
|
|
||||||
} // namespace detail
|
|
||||||
|
|
||||||
template <typename T>
|
|
||||||
struct iterator_traits<T*> {
|
|
||||||
typedef T value_type;
|
|
||||||
typedef T& reference;
|
|
||||||
typedef T* pointer;
|
|
||||||
typedef std::ptrdiff_t difference_type;
|
|
||||||
typedef typename detail::pointer_return_category<is_const<T>::value>::type
|
|
||||||
return_category;
|
|
||||||
typedef random_access_iterator_tag motion_category;
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif
|
|
||||||
|
|
||||||
} // namespace boost
|
|
||||||
|
|
||||||
#endif // BOOST_ITERATOR_TRAITS_HPP
|
|
@ -1,13 +0,0 @@
|
|||||||
#include <boost/iterator_concepts.hpp>
|
|
||||||
|
|
||||||
int
|
|
||||||
main()
|
|
||||||
{
|
|
||||||
boost::function_requires<
|
|
||||||
boost_concepts::MutableLvalueRandomAccessIteratorConcept<int*> >();
|
|
||||||
|
|
||||||
boost::function_requires<
|
|
||||||
boost_concepts::ConstantLvalueRandomAccessIteratorConcept<const int*> >();
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
76
doc/BidirectionalTraversal.html
Normal file
76
doc/BidirectionalTraversal.html
Normal file
@ -0,0 +1,76 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" />
|
||||||
|
<title>Bidirectional Traversal Concept</title>
|
||||||
|
<link rel="stylesheet" href="../../../rst.css" type="text/css" />
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="bidirectional-traversal-concept">
|
||||||
|
<h1 class="title">Bidirectional Traversal Concept</h1>
|
||||||
|
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<p>A class or built-in type <tt class="docutils literal"><span class="pre">X</span></tt> models the <em>Bidirectional Traversal</em>
|
||||||
|
concept if, in addition to <tt class="docutils literal"><span class="pre">X</span></tt> meeting the requirements of Forward
|
||||||
|
Traversal Iterator, the following expressions are valid and respect
|
||||||
|
the stated semantics.</p>
|
||||||
|
<table border="1" class="docutils">
|
||||||
|
<colgroup>
|
||||||
|
<col width="38%" />
|
||||||
|
<col width="37%" />
|
||||||
|
<col width="25%" />
|
||||||
|
</colgroup>
|
||||||
|
<thead valign="bottom">
|
||||||
|
<tr><th class="head" colspan="3">Bidirectional Traversal Iterator Requirements (in addition to Forward Traversal
|
||||||
|
Iterator)</th>
|
||||||
|
</tr>
|
||||||
|
<tr><th class="head">Expression</th>
|
||||||
|
<th class="head">Return Type</th>
|
||||||
|
<th class="head">Assertion/Semantics /
|
||||||
|
Pre-/Post-condition</th>
|
||||||
|
</tr>
|
||||||
|
</thead>
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">--r</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">X&</span></tt></td>
|
||||||
|
<td>pre: there exists
|
||||||
|
<tt class="docutils literal"><span class="pre">s</span></tt> such that <tt class="docutils literal"><span class="pre">r</span>
|
||||||
|
<span class="pre">==</span> <span class="pre">++s</span></tt>. post:
|
||||||
|
<tt class="docutils literal"><span class="pre">s</span></tt> is
|
||||||
|
dereferenceable.
|
||||||
|
<tt class="docutils literal"><span class="pre">--(++r)</span> <span class="pre">==</span> <span class="pre">r</span></tt>.
|
||||||
|
<tt class="docutils literal"><span class="pre">--r</span> <span class="pre">==</span> <span class="pre">--s</span></tt>
|
||||||
|
implies <tt class="docutils literal"><span class="pre">r</span> <span class="pre">==</span>
|
||||||
|
<span class="pre">s</span></tt>. <tt class="docutils literal"><span class="pre">&r</span> <span class="pre">==</span> <span class="pre">&--r</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">r--</span></tt></td>
|
||||||
|
<td>convertible to <tt class="docutils literal"><span class="pre">const</span> <span class="pre">X&</span></tt></td>
|
||||||
|
<td><pre class="first last literal-block">
|
||||||
|
{
|
||||||
|
X tmp = r;
|
||||||
|
--r;
|
||||||
|
return tmp;
|
||||||
|
}
|
||||||
|
</pre>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">iterator_traversal<X>::type</span></tt></td>
|
||||||
|
<td>Convertible to
|
||||||
|
<tt class="docutils literal"><span class="pre">bidirectional_traversal_tag</span></tt></td>
|
||||||
|
<td> </td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<hr class="footer" />
|
||||||
|
<a class="reference external" href="BidirectionalTraversal.rst">View document source</a>.
|
||||||
|
Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
41
doc/BidirectionalTraversal.rst
Normal file
41
doc/BidirectionalTraversal.rst
Normal file
@ -0,0 +1,41 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
Bidirectional Traversal Concept
|
||||||
|
...............................
|
||||||
|
|
||||||
|
A class or built-in type ``X`` models the *Bidirectional Traversal*
|
||||||
|
concept if, in addition to ``X`` meeting the requirements of Forward
|
||||||
|
Traversal Iterator, the following expressions are valid and respect
|
||||||
|
the stated semantics.
|
||||||
|
|
||||||
|
+--------------------------------------------------------------------------------------+
|
||||||
|
|Bidirectional Traversal Iterator Requirements (in addition to Forward Traversal |
|
||||||
|
|Iterator) |
|
||||||
|
+--------------------------------+-------------------------------+---------------------+
|
||||||
|
|Expression |Return Type |Assertion/Semantics /|
|
||||||
|
| | |Pre-/Post-condition |
|
||||||
|
+================================+===============================+=====================+
|
||||||
|
|``--r`` |``X&`` |pre: there exists |
|
||||||
|
| | |``s`` such that ``r |
|
||||||
|
| | |== ++s``. post: |
|
||||||
|
| | |``s`` is |
|
||||||
|
| | |dereferenceable. |
|
||||||
|
| | |``--(++r) == r``. |
|
||||||
|
| | |``--r == --s`` |
|
||||||
|
| | |implies ``r == |
|
||||||
|
| | |s``. ``&r == &--r``. |
|
||||||
|
+--------------------------------+-------------------------------+---------------------+
|
||||||
|
|``r--`` |convertible to ``const X&`` |:: |
|
||||||
|
| | | |
|
||||||
|
| | | { |
|
||||||
|
| | | X tmp = r; |
|
||||||
|
| | | --r; |
|
||||||
|
| | | return tmp; |
|
||||||
|
| | | } |
|
||||||
|
+--------------------------------+-------------------------------+---------------------+
|
||||||
|
|``iterator_traversal<X>::type`` |Convertible to | |
|
||||||
|
| |``bidirectional_traversal_tag``| |
|
||||||
|
| | | |
|
||||||
|
+--------------------------------+-------------------------------+---------------------+
|
67
doc/ForwardTraversal.html
Normal file
67
doc/ForwardTraversal.html
Normal file
@ -0,0 +1,67 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" />
|
||||||
|
<title>Forward Traversal Concept</title>
|
||||||
|
<link rel="stylesheet" href="../../../rst.css" type="text/css" />
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="forward-traversal-concept">
|
||||||
|
<h1 class="title">Forward Traversal Concept</h1>
|
||||||
|
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<p>A class or built-in type <tt class="docutils literal"><span class="pre">X</span></tt> models the <em>Forward Traversal</em>
|
||||||
|
concept if, in addition to <tt class="docutils literal"><span class="pre">X</span></tt> meeting the requirements of Default
|
||||||
|
Constructible and Single Pass Iterator, the following expressions are
|
||||||
|
valid and respect the stated semantics.</p>
|
||||||
|
<table border="1" class="docutils">
|
||||||
|
<colgroup>
|
||||||
|
<col width="38%" />
|
||||||
|
<col width="34%" />
|
||||||
|
<col width="27%" />
|
||||||
|
</colgroup>
|
||||||
|
<thead valign="bottom">
|
||||||
|
<tr><th class="head" colspan="3">Forward Traversal Iterator Requirements (in addition to Default Constructible and Single Pass Iterator)</th>
|
||||||
|
</tr>
|
||||||
|
<tr><th class="head">Expression</th>
|
||||||
|
<th class="head">Return Type</th>
|
||||||
|
<th class="head">Assertion/Note</th>
|
||||||
|
</tr>
|
||||||
|
</thead>
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">X</span> <span class="pre">u;</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">X&</span></tt></td>
|
||||||
|
<td>note: <tt class="docutils literal"><span class="pre">u</span></tt> may have a
|
||||||
|
singular value.</td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">++r</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">X&</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">r</span> <span class="pre">==</span> <span class="pre">s</span></tt> and <tt class="docutils literal"><span class="pre">r</span></tt> is
|
||||||
|
dereferenceable implies
|
||||||
|
<tt class="docutils literal"><span class="pre">++r</span> <span class="pre">==</span> <span class="pre">++s.</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">iterator_traits<X>::difference_type</span></tt></td>
|
||||||
|
<td>A signed integral type representing
|
||||||
|
the distance between iterators</td>
|
||||||
|
<td> </td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">iterator_traversal<X>::type</span></tt></td>
|
||||||
|
<td>Convertible to
|
||||||
|
<tt class="docutils literal"><span class="pre">forward_traversal_tag</span></tt></td>
|
||||||
|
<td> </td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<hr class="footer" />
|
||||||
|
<a class="reference external" href="ForwardTraversal.rst">View document source</a>.
|
||||||
|
Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
31
doc/ForwardTraversal.rst
Normal file
31
doc/ForwardTraversal.rst
Normal file
@ -0,0 +1,31 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
Forward Traversal Concept
|
||||||
|
.........................
|
||||||
|
|
||||||
|
A class or built-in type ``X`` models the *Forward Traversal*
|
||||||
|
concept if, in addition to ``X`` meeting the requirements of Default
|
||||||
|
Constructible and Single Pass Iterator, the following expressions are
|
||||||
|
valid and respect the stated semantics.
|
||||||
|
|
||||||
|
+--------------------------------------------------------------------------------------------------------+
|
||||||
|
|Forward Traversal Iterator Requirements (in addition to Default Constructible and Single Pass Iterator) |
|
||||||
|
+---------------------------------------+-----------------------------------+----------------------------+
|
||||||
|
|Expression |Return Type |Assertion/Note |
|
||||||
|
+=======================================+===================================+============================+
|
||||||
|
|``X u;`` |``X&`` |note: ``u`` may have a |
|
||||||
|
| | |singular value. |
|
||||||
|
+---------------------------------------+-----------------------------------+----------------------------+
|
||||||
|
|``++r`` |``X&`` |``r == s`` and ``r`` is |
|
||||||
|
| | |dereferenceable implies |
|
||||||
|
| | |``++r == ++s.`` |
|
||||||
|
+---------------------------------------+-----------------------------------+----------------------------+
|
||||||
|
|``iterator_traits<X>::difference_type``|A signed integral type representing| |
|
||||||
|
| |the distance between iterators | |
|
||||||
|
| | | |
|
||||||
|
+---------------------------------------+-----------------------------------+----------------------------+
|
||||||
|
|``iterator_traversal<X>::type`` |Convertible to | |
|
||||||
|
| |``forward_traversal_tag`` | |
|
||||||
|
+---------------------------------------+-----------------------------------+----------------------------+
|
15
doc/GNUmakefile
Normal file
15
doc/GNUmakefile
Normal file
@ -0,0 +1,15 @@
|
|||||||
|
# Copyright David Abrahams 2004. Distributed under the Boost
|
||||||
|
# Software License, Version 1.0. (See accompanying
|
||||||
|
# file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
ECHO = /bin/echo
|
||||||
|
|
||||||
|
all:
|
||||||
|
@${ECHO} "<boost-root>/libs/iterator/doc/GNUmakefile should be replaced by"
|
||||||
|
@${ECHO}
|
||||||
|
@${ECHO} " http://www.boost-consulting.com/writing/GNUmakefile,"
|
||||||
|
@${ECHO}
|
||||||
|
@${ECHO} "before proceeding. That file is not included in the Boost"
|
||||||
|
@${ECHO} "distribution because it is licensed under the GPL, which violates"
|
||||||
|
@${ECHO} "Boost license requirements."
|
||||||
|
|
66
doc/IncrementableIterator.html
Normal file
66
doc/IncrementableIterator.html
Normal file
@ -0,0 +1,66 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" />
|
||||||
|
<title>Incrementable Iterator Concept</title>
|
||||||
|
<link rel="stylesheet" href="../../../rst.css" type="text/css" />
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="incrementable-iterator-concept">
|
||||||
|
<h1 class="title">Incrementable Iterator Concept</h1>
|
||||||
|
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<p>A class or built-in type <tt class="docutils literal"><span class="pre">X</span></tt> models the <em>Incrementable Iterator</em>
|
||||||
|
concept if, in addition to <tt class="docutils literal"><span class="pre">X</span></tt> being Assignable and Copy
|
||||||
|
Constructible, the following expressions are valid and respect the
|
||||||
|
stated semantics.</p>
|
||||||
|
<table border="1" class="docutils">
|
||||||
|
<colgroup>
|
||||||
|
<col width="39%" />
|
||||||
|
<col width="37%" />
|
||||||
|
<col width="24%" />
|
||||||
|
</colgroup>
|
||||||
|
<thead valign="bottom">
|
||||||
|
<tr><th class="head" colspan="3">Incrementable Iterator Requirements (in addition to Assignable, Copy Constructible)</th>
|
||||||
|
</tr>
|
||||||
|
<tr><th class="head">Expression</th>
|
||||||
|
<th class="head">Return Type</th>
|
||||||
|
<th class="head">Assertion/Semantics</th>
|
||||||
|
</tr>
|
||||||
|
</thead>
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">++r</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">X&</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">&r</span> <span class="pre">==</span> <span class="pre">&++r</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">r++</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">X</span></tt></td>
|
||||||
|
<td><pre class="first last literal-block">
|
||||||
|
{
|
||||||
|
X tmp = r;
|
||||||
|
++r;
|
||||||
|
return tmp;
|
||||||
|
}
|
||||||
|
</pre>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">iterator_traversal<X>::type</span></tt></td>
|
||||||
|
<td>Convertible to
|
||||||
|
<tt class="docutils literal"><span class="pre">incrementable_traversal_tag</span></tt></td>
|
||||||
|
<td> </td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<hr class="footer" />
|
||||||
|
<a class="reference external" href="IncrementableIterator.rst">View document source</a>.
|
||||||
|
Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
32
doc/IncrementableIterator.rst
Normal file
32
doc/IncrementableIterator.rst
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
Incrementable Iterator Concept
|
||||||
|
..............................
|
||||||
|
|
||||||
|
A class or built-in type ``X`` models the *Incrementable Iterator*
|
||||||
|
concept if, in addition to ``X`` being Assignable and Copy
|
||||||
|
Constructible, the following expressions are valid and respect the
|
||||||
|
stated semantics.
|
||||||
|
|
||||||
|
|
||||||
|
+-------------------------------------------------------------------------------------+
|
||||||
|
|Incrementable Iterator Requirements (in addition to Assignable, Copy Constructible) |
|
||||||
|
| |
|
||||||
|
+--------------------------------+-------------------------------+--------------------+
|
||||||
|
|Expression |Return Type |Assertion/Semantics |
|
||||||
|
+================================+===============================+====================+
|
||||||
|
|``++r`` |``X&`` |``&r == &++r`` |
|
||||||
|
+--------------------------------+-------------------------------+--------------------+
|
||||||
|
|``r++`` |``X`` |:: |
|
||||||
|
| | | |
|
||||||
|
| | | { |
|
||||||
|
| | | X tmp = r; |
|
||||||
|
| | | ++r; |
|
||||||
|
| | | return tmp; |
|
||||||
|
| | | } |
|
||||||
|
+--------------------------------+-------------------------------+--------------------+
|
||||||
|
|``iterator_traversal<X>::type`` |Convertible to | |
|
||||||
|
| |``incrementable_traversal_tag``| |
|
||||||
|
+--------------------------------+-------------------------------+--------------------+
|
61
doc/InteroperableIterator.rst
Normal file
61
doc/InteroperableIterator.rst
Normal file
@ -0,0 +1,61 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
Interoperable Iterator Concept
|
||||||
|
..............................
|
||||||
|
|
||||||
|
A class or built-in type ``X`` that models Single Pass Iterator is
|
||||||
|
*interoperable with* a class or built-in type ``Y`` that also models
|
||||||
|
Single Pass Iterator if the following expressions are valid and
|
||||||
|
respect the stated semantics. In the tables below, ``x`` is an object
|
||||||
|
of type ``X``, ``y`` is an object of type ``Y``, ``Distance`` is
|
||||||
|
``iterator_traits<Y>::difference_type``, and ``n`` represents a
|
||||||
|
constant object of type ``Distance``.
|
||||||
|
|
||||||
|
+-----------+-----------------------+---------------------------------------------------+
|
||||||
|
|Expression |Return Type |Assertion/Precondition/Postcondition |
|
||||||
|
+===========+=======================+===================================================+
|
||||||
|
|``y = x`` |``Y`` |post: ``y == x`` |
|
||||||
|
+-----------+-----------------------+---------------------------------------------------+
|
||||||
|
|``Y(x)`` |``Y`` |post: ``Y(x) == x`` |
|
||||||
|
+-----------+-----------------------+---------------------------------------------------+
|
||||||
|
|``x == y`` |convertible to ``bool``|``==`` is an equivalence relation over its domain. |
|
||||||
|
+-----------+-----------------------+---------------------------------------------------+
|
||||||
|
|``y == x`` |convertible to ``bool``|``==`` is an equivalence relation over its domain. |
|
||||||
|
+-----------+-----------------------+---------------------------------------------------+
|
||||||
|
|``x != y`` |convertible to ``bool``|``bool(a==b) != bool(a!=b)`` over its domain. |
|
||||||
|
+-----------+-----------------------+---------------------------------------------------+
|
||||||
|
|``y != x`` |convertible to ``bool``|``bool(a==b) != bool(a!=b)`` over its domain. |
|
||||||
|
+-----------+-----------------------+---------------------------------------------------+
|
||||||
|
|
||||||
|
If ``X`` and ``Y`` both model Random Access Traversal Iterator then
|
||||||
|
the following additional requirements must be met.
|
||||||
|
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|Expression |Return Type |Operational Semantics|Assertion/ Precondition |
|
||||||
|
+===========+=======================+=====================+======================================+
|
||||||
|
|``x < y`` |convertible to ``bool``|``y - x > 0`` |``<`` is a total ordering relation |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|``y < x`` |convertible to ``bool``|``x - y > 0`` |``<`` is a total ordering relation |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|``x > y`` |convertible to ``bool``|``y < x`` |``>`` is a total ordering relation |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|``y > x`` |convertible to ``bool``|``x < y`` |``>`` is a total ordering relation |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|``x >= y`` |convertible to ``bool``|``!(x < y)`` | |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|``y >= x`` |convertible to ``bool``|``!(y < x)`` | |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|``x <= y`` |convertible to ``bool``|``!(x > y)`` | |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|``y <= x`` |convertible to ``bool``|``!(y > x)`` | |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|``y - x`` |``Distance`` |``distance(Y(x),y)`` |pre: there exists a value ``n`` of |
|
||||||
|
| | | |``Distance`` such that ``x + n == y``.|
|
||||||
|
| | | |``y == x + (y - x)``. |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|``x - y`` |``Distance`` |``distance(y,Y(x))`` |pre: there exists a value ``n`` of |
|
||||||
|
| | | |``Distance`` such that ``y + n == x``.|
|
||||||
|
| | | |``x == y + (x - y)``. |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
20
doc/Jamfile.v2
Normal file
20
doc/Jamfile.v2
Normal file
@ -0,0 +1,20 @@
|
|||||||
|
# Copyright Thomas Witt 2005. Use, modification, and distribution are
|
||||||
|
# subject to the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
# file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
using quickbook ;
|
||||||
|
|
||||||
|
xml iterator
|
||||||
|
:
|
||||||
|
quickbook/iterator.qbk
|
||||||
|
;
|
||||||
|
|
||||||
|
boostbook standalone
|
||||||
|
:
|
||||||
|
iterator
|
||||||
|
:
|
||||||
|
<xsl:param>toc.max.depth=3
|
||||||
|
<xsl:param>toc.section.depth=3
|
||||||
|
<xsl:param>chunk.section.depth=4
|
||||||
|
;
|
||||||
|
|
56
doc/LvalueIterator.html
Normal file
56
doc/LvalueIterator.html
Normal file
@ -0,0 +1,56 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" />
|
||||||
|
<title>Lvalue Iterator Concept</title>
|
||||||
|
<link rel="stylesheet" href="../../../rst.css" type="text/css" />
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="lvalue-iterator-concept">
|
||||||
|
<h1 class="title">Lvalue Iterator Concept</h1>
|
||||||
|
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<p>The <em>Lvalue Iterator</em> concept adds the requirement that the return
|
||||||
|
type of <tt class="docutils literal"><span class="pre">operator*</span></tt> type be a reference to the value type of the
|
||||||
|
iterator.</p>
|
||||||
|
<table border="1" class="docutils">
|
||||||
|
<colgroup>
|
||||||
|
<col width="22%" />
|
||||||
|
<col width="19%" />
|
||||||
|
<col width="59%" />
|
||||||
|
</colgroup>
|
||||||
|
<thead valign="bottom">
|
||||||
|
<tr><th class="head" colspan="3">Lvalue Iterator Requirements</th>
|
||||||
|
</tr>
|
||||||
|
<tr><th class="head">Expression</th>
|
||||||
|
<th class="head">Return Type</th>
|
||||||
|
<th class="head">Note/Assertion</th>
|
||||||
|
</tr>
|
||||||
|
</thead>
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">*a</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">T&</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">T</span></tt> is <em>cv</em>
|
||||||
|
<tt class="docutils literal"><span class="pre">iterator_traits<X>::value_type</span></tt>
|
||||||
|
where <em>cv</em> is an optional
|
||||||
|
cv-qualification.
|
||||||
|
pre: <tt class="docutils literal"><span class="pre">a</span></tt> is
|
||||||
|
dereferenceable. If <tt class="docutils literal"><span class="pre">a</span>
|
||||||
|
<span class="pre">==</span> <span class="pre">b</span></tt> then <tt class="docutils literal"><span class="pre">*a</span></tt> is
|
||||||
|
equivalent to <tt class="docutils literal"><span class="pre">*b</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<hr class="footer" />
|
||||||
|
<a class="reference external" href="LvalueIterator.rst">View document source</a>.
|
||||||
|
Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
25
doc/LvalueIterator.rst
Normal file
25
doc/LvalueIterator.rst
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
Lvalue Iterator Concept
|
||||||
|
.......................
|
||||||
|
|
||||||
|
The *Lvalue Iterator* concept adds the requirement that the return
|
||||||
|
type of ``operator*`` type be a reference to the value type of the
|
||||||
|
iterator.
|
||||||
|
|
||||||
|
+-------------------------------------------------------------+
|
||||||
|
| Lvalue Iterator Requirements |
|
||||||
|
+-------------+-----------+-----------------------------------+
|
||||||
|
|Expression |Return Type|Note/Assertion |
|
||||||
|
+=============+===========+===================================+
|
||||||
|
|``*a`` | ``T&`` |``T`` is *cv* |
|
||||||
|
| | |``iterator_traits<X>::value_type`` |
|
||||||
|
| | |where *cv* is an optional |
|
||||||
|
| | |cv-qualification. |
|
||||||
|
| | |pre: ``a`` is |
|
||||||
|
| | |dereferenceable. If ``a |
|
||||||
|
| | |== b`` then ``*a`` is |
|
||||||
|
| | |equivalent to ``*b``. |
|
||||||
|
+-------------+-----------+-----------------------------------+
|
134
doc/RandomAccessTraversal.html
Normal file
134
doc/RandomAccessTraversal.html
Normal file
@ -0,0 +1,134 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" />
|
||||||
|
<title>Random Access Traversal Concept</title>
|
||||||
|
<link rel="stylesheet" href="../../../rst.css" type="text/css" />
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="random-access-traversal-concept">
|
||||||
|
<h1 class="title">Random Access Traversal Concept</h1>
|
||||||
|
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<p>A class or built-in type <tt class="docutils literal"><span class="pre">X</span></tt> models the <em>Random Access Traversal</em>
|
||||||
|
concept if the following expressions are valid and respect the stated
|
||||||
|
semantics. In the table below, <tt class="docutils literal"><span class="pre">Distance</span></tt> is
|
||||||
|
<tt class="docutils literal"><span class="pre">iterator_traits<X>::difference_type</span></tt> and <tt class="docutils literal"><span class="pre">n</span></tt> represents a
|
||||||
|
constant object of type <tt class="docutils literal"><span class="pre">Distance</span></tt>.</p>
|
||||||
|
<table border="1" class="docutils">
|
||||||
|
<colgroup>
|
||||||
|
<col width="28%" />
|
||||||
|
<col width="30%" />
|
||||||
|
<col width="23%" />
|
||||||
|
<col width="20%" />
|
||||||
|
</colgroup>
|
||||||
|
<thead valign="bottom">
|
||||||
|
<tr><th class="head" colspan="4">Random Access Traversal Iterator Requirements (in addition to Bidirectional Traversal)</th>
|
||||||
|
</tr>
|
||||||
|
<tr><th class="head">Expression</th>
|
||||||
|
<th class="head">Return Type</th>
|
||||||
|
<th class="head">Operational Semantics</th>
|
||||||
|
<th class="head">Assertion/
|
||||||
|
Precondition</th>
|
||||||
|
</tr>
|
||||||
|
</thead>
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">r</span> <span class="pre">+=</span> <span class="pre">n</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">X&</span></tt></td>
|
||||||
|
<td><pre class="first last literal-block">
|
||||||
|
{
|
||||||
|
Distance m = n;
|
||||||
|
if (m >= 0)
|
||||||
|
while (m--)
|
||||||
|
++r;
|
||||||
|
else
|
||||||
|
while (m++)
|
||||||
|
--r;
|
||||||
|
return r;
|
||||||
|
}
|
||||||
|
</pre>
|
||||||
|
</td>
|
||||||
|
<td> </td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">a</span> <span class="pre">+</span> <span class="pre">n</span></tt>, <tt class="docutils literal"><span class="pre">n</span> <span class="pre">+</span> <span class="pre">a</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">X</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">{</span> <span class="pre">X</span> <span class="pre">tmp</span> <span class="pre">=</span> <span class="pre">a;</span> <span class="pre">return</span> <span class="pre">tmp</span>
|
||||||
|
<span class="pre">+=</span> <span class="pre">n;</span> <span class="pre">}</span></tt></td>
|
||||||
|
<td> </td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">r</span> <span class="pre">-=</span> <span class="pre">n</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">X&</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">return</span> <span class="pre">r</span> <span class="pre">+=</span> <span class="pre">-n</span></tt></td>
|
||||||
|
<td> </td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">a</span> <span class="pre">-</span> <span class="pre">n</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">X</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">{</span> <span class="pre">X</span> <span class="pre">tmp</span> <span class="pre">=</span> <span class="pre">a;</span> <span class="pre">return</span> <span class="pre">tmp</span>
|
||||||
|
<span class="pre">-=</span> <span class="pre">n;</span> <span class="pre">}</span></tt></td>
|
||||||
|
<td> </td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">b</span> <span class="pre">-</span> <span class="pre">a</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">Distance</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">a</span> <span class="pre"><</span> <span class="pre">b</span> <span class="pre">?</span> <span class="pre">distance(a,b)</span>
|
||||||
|
<span class="pre">:</span> <span class="pre">-distance(b,a)</span></tt></td>
|
||||||
|
<td>pre: there exists a
|
||||||
|
value <tt class="docutils literal"><span class="pre">n</span></tt> of
|
||||||
|
<tt class="docutils literal"><span class="pre">Distance</span></tt> such that
|
||||||
|
<tt class="docutils literal"><span class="pre">a</span> <span class="pre">+</span> <span class="pre">n</span> <span class="pre">==</span> <span class="pre">b</span></tt>. <tt class="docutils literal"><span class="pre">b</span>
|
||||||
|
<span class="pre">==</span> <span class="pre">a</span> <span class="pre">+</span> <span class="pre">(b</span> <span class="pre">-</span> <span class="pre">a)</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">a[n]</span></tt></td>
|
||||||
|
<td>convertible to T</td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">*(a</span> <span class="pre">+</span> <span class="pre">n)</span></tt></td>
|
||||||
|
<td>pre: a is a <em>Readable
|
||||||
|
Iterator</em></td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">a[n]</span> <span class="pre">=</span> <span class="pre">v</span></tt></td>
|
||||||
|
<td>convertible to T</td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">*(a</span> <span class="pre">+</span> <span class="pre">n)</span> <span class="pre">=</span> <span class="pre">v</span></tt></td>
|
||||||
|
<td>pre: a is a <em>Writable
|
||||||
|
iterator</em></td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">a</span> <span class="pre"><</span> <span class="pre">b</span></tt></td>
|
||||||
|
<td>convertible to <tt class="docutils literal"><span class="pre">bool</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">b</span> <span class="pre">-</span> <span class="pre">a</span> <span class="pre">></span> <span class="pre">0</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre"><</span></tt> is a total
|
||||||
|
ordering relation</td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">a</span> <span class="pre">></span> <span class="pre">b</span></tt></td>
|
||||||
|
<td>convertible to <tt class="docutils literal"><span class="pre">bool</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">b</span> <span class="pre"><</span> <span class="pre">a</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">></span></tt> is a total
|
||||||
|
ordering relation</td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">a</span> <span class="pre">>=</span> <span class="pre">b</span></tt></td>
|
||||||
|
<td>convertible to <tt class="docutils literal"><span class="pre">bool</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">!(a</span> <span class="pre"><</span> <span class="pre">b)</span></tt></td>
|
||||||
|
<td> </td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">a</span> <span class="pre"><=</span> <span class="pre">b</span></tt></td>
|
||||||
|
<td>convertible to <tt class="docutils literal"><span class="pre">bool</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">!(a</span> <span class="pre">></span> <span class="pre">b)</span></tt></td>
|
||||||
|
<td> </td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">iterator_traversal<X>::type</span></tt></td>
|
||||||
|
<td>Convertible to
|
||||||
|
<tt class="docutils literal"><span class="pre">random_access_traversal_tag</span></tt></td>
|
||||||
|
<td> </td>
|
||||||
|
<td> </td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<hr class="footer" />
|
||||||
|
<a class="reference external" href="RandomAccessTraversal.rst">View document source</a>.
|
||||||
|
Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
67
doc/RandomAccessTraversal.rst
Normal file
67
doc/RandomAccessTraversal.rst
Normal file
@ -0,0 +1,67 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
Random Access Traversal Concept
|
||||||
|
...............................
|
||||||
|
|
||||||
|
A class or built-in type ``X`` models the *Random Access Traversal*
|
||||||
|
concept if the following expressions are valid and respect the stated
|
||||||
|
semantics. In the table below, ``Distance`` is
|
||||||
|
``iterator_traits<X>::difference_type`` and ``n`` represents a
|
||||||
|
constant object of type ``Distance``.
|
||||||
|
|
||||||
|
+------------------------------------------------------------------------------------------------------------------+
|
||||||
|
|Random Access Traversal Iterator Requirements (in addition to Bidirectional Traversal) |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|Expression |Return Type |Operational Semantics |Assertion/ |
|
||||||
|
| | | |Precondition |
|
||||||
|
+===============================+=================================+=========================+======================+
|
||||||
|
|``r += n`` |``X&`` |:: | |
|
||||||
|
| | | | |
|
||||||
|
| | | { | |
|
||||||
|
| | | Distance m = n; | |
|
||||||
|
| | | if (m >= 0) | |
|
||||||
|
| | | while (m--) | |
|
||||||
|
| | | ++r; | |
|
||||||
|
| | | else | |
|
||||||
|
| | | while (m++) | |
|
||||||
|
| | | --r; | |
|
||||||
|
| | | return r; | |
|
||||||
|
| | | } | |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``a + n``, ``n + a`` |``X`` |``{ X tmp = a; return tmp| |
|
||||||
|
| | |+= n; }`` | |
|
||||||
|
| | | | |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``r -= n`` |``X&`` |``return r += -n`` | |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``a - n`` |``X`` |``{ X tmp = a; return tmp| |
|
||||||
|
| | |-= n; }`` | |
|
||||||
|
| | | | |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``b - a`` |``Distance`` |``a < b ? distance(a,b) |pre: there exists a |
|
||||||
|
| | |: -distance(b,a)`` |value ``n`` of |
|
||||||
|
| | | |``Distance`` such that|
|
||||||
|
| | | |``a + n == b``. ``b |
|
||||||
|
| | | |== a + (b - a)``. |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``a[n]`` |convertible to T |``*(a + n)`` |pre: a is a *Readable |
|
||||||
|
| | | |Iterator* |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``a[n] = v`` |convertible to T |``*(a + n) = v`` |pre: a is a *Writable |
|
||||||
|
| | | |iterator* |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``a < b`` |convertible to ``bool`` |``b - a > 0`` |``<`` is a total |
|
||||||
|
| | | |ordering relation |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``a > b`` |convertible to ``bool`` |``b < a`` |``>`` is a total |
|
||||||
|
| | | |ordering relation |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``a >= b`` |convertible to ``bool`` |``!(a < b)`` | |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``a <= b`` |convertible to ``bool`` |``!(a > b)`` | |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``iterator_traversal<X>::type``|Convertible to | | |
|
||||||
|
| |``random_access_traversal_tag`` | | |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
64
doc/ReadableIterator.html
Normal file
64
doc/ReadableIterator.html
Normal file
@ -0,0 +1,64 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" />
|
||||||
|
<title>Readable Iterator Concept</title>
|
||||||
|
<link rel="stylesheet" href="../../../rst.css" type="text/css" />
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="readable-iterator-concept">
|
||||||
|
<h1 class="title">Readable Iterator Concept</h1>
|
||||||
|
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<p>A class or built-in type <tt class="docutils literal"><span class="pre">X</span></tt> models the <em>Readable Iterator</em> concept
|
||||||
|
for value type <tt class="docutils literal"><span class="pre">T</span></tt> if, in addition to <tt class="docutils literal"><span class="pre">X</span></tt> being Assignable and
|
||||||
|
Copy Constructible, the following expressions are valid and respect
|
||||||
|
the stated semantics. <tt class="docutils literal"><span class="pre">U</span></tt> is the type of any specified member of
|
||||||
|
type <tt class="docutils literal"><span class="pre">T</span></tt>.</p>
|
||||||
|
<table border="1" class="docutils">
|
||||||
|
<colgroup>
|
||||||
|
<col width="28%" />
|
||||||
|
<col width="20%" />
|
||||||
|
<col width="52%" />
|
||||||
|
</colgroup>
|
||||||
|
<thead valign="bottom">
|
||||||
|
<tr><th class="head" colspan="3">Readable Iterator Requirements (in addition to Assignable and Copy Constructible)</th>
|
||||||
|
</tr>
|
||||||
|
<tr><th class="head">Expression</th>
|
||||||
|
<th class="head">Return Type</th>
|
||||||
|
<th class="head">Note/Precondition</th>
|
||||||
|
</tr>
|
||||||
|
</thead>
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">iterator_traits<X>::value_type</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">T</span></tt></td>
|
||||||
|
<td>Any non-reference,
|
||||||
|
non-cv-qualified type</td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">*a</span></tt></td>
|
||||||
|
<td>Convertible to <tt class="docutils literal"><span class="pre">T</span></tt></td>
|
||||||
|
<td><dl class="first last docutils">
|
||||||
|
<dt>pre: <tt class="docutils literal"><span class="pre">a</span></tt> is dereferenceable. If <tt class="docutils literal"><span class="pre">a</span> <span class="pre">==</span> <span class="pre">b</span></tt> then <tt class="docutils literal"><span class="pre">*a</span></tt></dt>
|
||||||
|
<dd>is equivalent to <tt class="docutils literal"><span class="pre">*b</span></tt>.</dd>
|
||||||
|
</dl>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">a->m</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">U&</span></tt></td>
|
||||||
|
<td>pre: <tt class="docutils literal"><span class="pre">pre:</span> <span class="pre">(*a).m</span></tt> is well-defined. Equivalent to <tt class="docutils literal"><span class="pre">(*a).m</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<hr class="footer" />
|
||||||
|
<a class="reference external" href="ReadableIterator.rst">View document source</a>.
|
||||||
|
Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
26
doc/ReadableIterator.rst
Normal file
26
doc/ReadableIterator.rst
Normal file
@ -0,0 +1,26 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
Readable Iterator Concept
|
||||||
|
.........................
|
||||||
|
|
||||||
|
A class or built-in type ``X`` models the *Readable Iterator* concept
|
||||||
|
for value type ``T`` if, in addition to ``X`` being Assignable and
|
||||||
|
Copy Constructible, the following expressions are valid and respect
|
||||||
|
the stated semantics. ``U`` is the type of any specified member of
|
||||||
|
type ``T``.
|
||||||
|
|
||||||
|
+-----------------------------------------------------------------------------------------------------------------------------+
|
||||||
|
|Readable Iterator Requirements (in addition to Assignable and Copy Constructible) |
|
||||||
|
+-----------------------------------+------------------------+----------------------------------------------------------------+
|
||||||
|
|Expression |Return Type |Note/Precondition |
|
||||||
|
+===================================+========================+================================================================+
|
||||||
|
|``iterator_traits<X>::value_type`` |``T`` |Any non-reference, |
|
||||||
|
| | |non-cv-qualified type |
|
||||||
|
+-----------------------------------+------------------------+----------------------------------------------------------------+
|
||||||
|
|``*a`` | Convertible to ``T`` |pre: ``a`` is dereferenceable. If ``a == b`` then ``*a`` |
|
||||||
|
| | | is equivalent to ``*b``. |
|
||||||
|
+-----------------------------------+------------------------+----------------------------------------------------------------+
|
||||||
|
|``a->m`` |``U&`` |pre: ``pre: (*a).m`` is well-defined. Equivalent to ``(*a).m``. |
|
||||||
|
+-----------------------------------+------------------------+----------------------------------------------------------------+
|
68
doc/SinglePassIterator.html
Normal file
68
doc/SinglePassIterator.html
Normal file
@ -0,0 +1,68 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" />
|
||||||
|
<title>Single Pass Iterator Concept</title>
|
||||||
|
<link rel="stylesheet" href="../../../rst.css" type="text/css" />
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="single-pass-iterator-concept">
|
||||||
|
<h1 class="title">Single Pass Iterator Concept</h1>
|
||||||
|
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<p>A class or built-in type <tt class="docutils literal"><span class="pre">X</span></tt> models the <em>Single Pass Iterator</em>
|
||||||
|
concept if the following expressions are valid and respect the stated
|
||||||
|
semantics.</p>
|
||||||
|
<table border="1" class="docutils">
|
||||||
|
<colgroup>
|
||||||
|
<col width="36%" />
|
||||||
|
<col width="33%" />
|
||||||
|
<col width="31%" />
|
||||||
|
</colgroup>
|
||||||
|
<thead valign="bottom">
|
||||||
|
<tr><th class="head" colspan="3">Single Pass Iterator Requirements (in addition to Incrementable Iterator and Equality
|
||||||
|
Comparable)</th>
|
||||||
|
</tr>
|
||||||
|
<tr><th class="head">Expression</th>
|
||||||
|
<th class="head">Return Type</th>
|
||||||
|
<th class="head">Assertion/Semantics /
|
||||||
|
Pre-/Post-condition</th>
|
||||||
|
</tr>
|
||||||
|
</thead>
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">++r</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">X&</span></tt></td>
|
||||||
|
<td>pre: <tt class="docutils literal"><span class="pre">r</span></tt> is
|
||||||
|
dereferenceable; post:
|
||||||
|
<tt class="docutils literal"><span class="pre">r</span></tt> is dereferenceable or
|
||||||
|
<tt class="docutils literal"><span class="pre">r</span></tt> is past-the-end</td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">a</span> <span class="pre">==</span> <span class="pre">b</span></tt></td>
|
||||||
|
<td>convertible to <tt class="docutils literal"><span class="pre">bool</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">==</span></tt> is an equivalence
|
||||||
|
relation over its domain</td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">a</span> <span class="pre">!=</span> <span class="pre">b</span></tt></td>
|
||||||
|
<td>convertible to <tt class="docutils literal"><span class="pre">bool</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">!(a</span> <span class="pre">==</span> <span class="pre">b)</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">iterator_traversal<X>::type</span></tt></td>
|
||||||
|
<td>Convertible to
|
||||||
|
<tt class="docutils literal"><span class="pre">single_pass_traversal_tag</span></tt></td>
|
||||||
|
<td> </td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<hr class="footer" />
|
||||||
|
<a class="reference external" href="SinglePassIterator.rst">View document source</a>.
|
||||||
|
Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
32
doc/SinglePassIterator.rst
Normal file
32
doc/SinglePassIterator.rst
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
Single Pass Iterator Concept
|
||||||
|
............................
|
||||||
|
|
||||||
|
A class or built-in type ``X`` models the *Single Pass Iterator*
|
||||||
|
concept if the following expressions are valid and respect the stated
|
||||||
|
semantics.
|
||||||
|
|
||||||
|
|
||||||
|
+------------------------------------------------------------------------------------------+
|
||||||
|
|Single Pass Iterator Requirements (in addition to Incrementable Iterator and Equality |
|
||||||
|
|Comparable) |
|
||||||
|
+--------------------------------+-----------------------------+---------------------------+
|
||||||
|
|Expression |Return Type |Assertion/Semantics / |
|
||||||
|
| | |Pre-/Post-condition |
|
||||||
|
+================================+=============================+===========================+
|
||||||
|
|``++r`` |``X&`` |pre: ``r`` is |
|
||||||
|
| | |dereferenceable; post: |
|
||||||
|
| | |``r`` is dereferenceable or|
|
||||||
|
| | |``r`` is past-the-end |
|
||||||
|
+--------------------------------+-----------------------------+---------------------------+
|
||||||
|
|``a == b`` |convertible to ``bool`` |``==`` is an equivalence |
|
||||||
|
| | |relation over its domain |
|
||||||
|
+--------------------------------+-----------------------------+---------------------------+
|
||||||
|
|``a != b`` |convertible to ``bool`` |``!(a == b)`` |
|
||||||
|
+--------------------------------+-----------------------------+---------------------------+
|
||||||
|
|``iterator_traversal<X>::type`` |Convertible to | |
|
||||||
|
| |``single_pass_traversal_tag``| |
|
||||||
|
+--------------------------------+-----------------------------+---------------------------+
|
54
doc/SwappableIterator.html
Normal file
54
doc/SwappableIterator.html
Normal file
@ -0,0 +1,54 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" />
|
||||||
|
<title>Swappable Iterator Concept</title>
|
||||||
|
<link rel="stylesheet" href="../../../rst.css" type="text/css" />
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="swappable-iterator-concept">
|
||||||
|
<h1 class="title">Swappable Iterator Concept</h1>
|
||||||
|
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<p>A class or built-in type <tt class="docutils literal"><span class="pre">X</span></tt> models the <em>Swappable Iterator</em> concept
|
||||||
|
if, in addition to <tt class="docutils literal"><span class="pre">X</span></tt> being Copy Constructible, the following
|
||||||
|
expressions are valid and respect the stated semantics.</p>
|
||||||
|
<table border="1" class="docutils">
|
||||||
|
<colgroup>
|
||||||
|
<col width="37%" />
|
||||||
|
<col width="19%" />
|
||||||
|
<col width="43%" />
|
||||||
|
</colgroup>
|
||||||
|
<thead valign="bottom">
|
||||||
|
<tr><th class="head" colspan="3">Swappable Iterator Requirements (in addition to Copy Constructible)</th>
|
||||||
|
</tr>
|
||||||
|
<tr><th class="head">Expression</th>
|
||||||
|
<th class="head">Return Type</th>
|
||||||
|
<th class="head">Postcondition</th>
|
||||||
|
</tr>
|
||||||
|
</thead>
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">iter_swap(a,</span> <span class="pre">b)</span></tt></td>
|
||||||
|
<td><tt class="docutils literal"><span class="pre">void</span></tt></td>
|
||||||
|
<td>the pointed to values are
|
||||||
|
exchanged</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<dl class="docutils">
|
||||||
|
<dt>[<em>Note:</em> An iterator that is a model of the <em>Readable</em> and <em>Writable Iterator</em> concepts</dt>
|
||||||
|
<dd>is also a model of <em>Swappable Iterator</em>. <em>--end note</em>]</dd>
|
||||||
|
</dl>
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<hr class="footer" />
|
||||||
|
<a class="reference external" href="SwappableIterator.rst">View document source</a>.
|
||||||
|
Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
23
doc/SwappableIterator.rst
Normal file
23
doc/SwappableIterator.rst
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
Swappable Iterator Concept
|
||||||
|
..........................
|
||||||
|
|
||||||
|
A class or built-in type ``X`` models the *Swappable Iterator* concept
|
||||||
|
if, in addition to ``X`` being Copy Constructible, the following
|
||||||
|
expressions are valid and respect the stated semantics.
|
||||||
|
|
||||||
|
+---------------------------------------------------------------------+
|
||||||
|
|Swappable Iterator Requirements (in addition to Copy Constructible) |
|
||||||
|
+-------------------------+-------------+-----------------------------+
|
||||||
|
|Expression |Return Type |Postcondition |
|
||||||
|
+=========================+=============+=============================+
|
||||||
|
|``iter_swap(a, b)`` |``void`` |the pointed to values are |
|
||||||
|
| | |exchanged |
|
||||||
|
+-------------------------+-------------+-----------------------------+
|
||||||
|
|
||||||
|
[*Note:* An iterator that is a model of the *Readable* and *Writable Iterator* concepts
|
||||||
|
is also a model of *Swappable Iterator*. *--end note*]
|
||||||
|
|
52
doc/WritableIterator.html
Normal file
52
doc/WritableIterator.html
Normal file
@ -0,0 +1,52 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" />
|
||||||
|
<title>Writable Iterator Concept</title>
|
||||||
|
<link rel="stylesheet" href="../../../rst.css" type="text/css" />
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="writable-iterator-concept">
|
||||||
|
<h1 class="title">Writable Iterator Concept</h1>
|
||||||
|
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<p>A class or built-in type <tt class="docutils literal"><span class="pre">X</span></tt> models the <em>Writable Iterator</em> concept
|
||||||
|
if, in addition to <tt class="docutils literal"><span class="pre">X</span></tt> being Copy Constructible, the following
|
||||||
|
expressions are valid and respect the stated semantics. Writable
|
||||||
|
Iterators have an associated <em>set of value types</em>.</p>
|
||||||
|
<table border="1" class="docutils">
|
||||||
|
<colgroup>
|
||||||
|
<col width="37%" />
|
||||||
|
<col width="21%" />
|
||||||
|
<col width="42%" />
|
||||||
|
</colgroup>
|
||||||
|
<thead valign="bottom">
|
||||||
|
<tr><th class="head" colspan="3">Writable Iterator Requirements (in addition to Copy Constructible)</th>
|
||||||
|
</tr>
|
||||||
|
<tr><th class="head">Expression</th>
|
||||||
|
<th class="head">Return Type</th>
|
||||||
|
<th class="head">Precondition</th>
|
||||||
|
</tr>
|
||||||
|
</thead>
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><td><tt class="docutils literal"><span class="pre">*a</span> <span class="pre">=</span> <span class="pre">o</span></tt></td>
|
||||||
|
<td> </td>
|
||||||
|
<td>pre: The type of <tt class="docutils literal"><span class="pre">o</span></tt>
|
||||||
|
is in the set of
|
||||||
|
value types of <tt class="docutils literal"><span class="pre">X</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<hr class="footer" />
|
||||||
|
<a class="reference external" href="WritableIterator.rst">View document source</a>.
|
||||||
|
Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
21
doc/WritableIterator.rst
Normal file
21
doc/WritableIterator.rst
Normal file
@ -0,0 +1,21 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
Writable Iterator Concept
|
||||||
|
.........................
|
||||||
|
|
||||||
|
A class or built-in type ``X`` models the *Writable Iterator* concept
|
||||||
|
if, in addition to ``X`` being Copy Constructible, the following
|
||||||
|
expressions are valid and respect the stated semantics. Writable
|
||||||
|
Iterators have an associated *set of value types*.
|
||||||
|
|
||||||
|
+---------------------------------------------------------------------+
|
||||||
|
|Writable Iterator Requirements (in addition to Copy Constructible) |
|
||||||
|
+-------------------------+--------------+----------------------------+
|
||||||
|
|Expression |Return Type |Precondition |
|
||||||
|
+=========================+==============+============================+
|
||||||
|
|``*a = o`` | | pre: The type of ``o`` |
|
||||||
|
| | | is in the set of |
|
||||||
|
| | | value types of ``X`` |
|
||||||
|
+-------------------------+--------------+----------------------------+
|
BIN
doc/access.png
Normal file
BIN
doc/access.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 11 KiB |
BIN
doc/access2old.png
Normal file
BIN
doc/access2old.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 41 KiB |
301
doc/counting_iterator.html
Normal file
301
doc/counting_iterator.html
Normal file
@ -0,0 +1,301 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" />
|
||||||
|
<title>Counting Iterator</title>
|
||||||
|
<meta name="author" content="David Abrahams, Jeremy Siek, Thomas Witt" />
|
||||||
|
<meta name="organization" content="Boost Consulting, Indiana University Open Systems Lab, University of Hanover Institute for Transport Railway Operation and Construction" />
|
||||||
|
<meta name="date" content="2006-09-11" />
|
||||||
|
<meta name="copyright" content="Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003." />
|
||||||
|
<link rel="stylesheet" href="../../../rst.css" type="text/css" />
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="counting-iterator">
|
||||||
|
<h1 class="title">Counting Iterator</h1>
|
||||||
|
<table class="docinfo" frame="void" rules="none">
|
||||||
|
<col class="docinfo-name" />
|
||||||
|
<col class="docinfo-content" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><th class="docinfo-name">Author:</th>
|
||||||
|
<td>David Abrahams, Jeremy Siek, Thomas Witt</td></tr>
|
||||||
|
<tr><th class="docinfo-name">Contact:</th>
|
||||||
|
<td><a class="first reference external" href="mailto:dave@boost-consulting.com">dave@boost-consulting.com</a>, <a class="reference external" href="mailto:jsiek@osl.iu.edu">jsiek@osl.iu.edu</a>, <a class="last reference external" href="mailto:witt@ive.uni-hannover.de">witt@ive.uni-hannover.de</a></td></tr>
|
||||||
|
<tr><th class="docinfo-name">Organization:</th>
|
||||||
|
<td><a class="first reference external" href="http://www.boost-consulting.com">Boost Consulting</a>, Indiana University <a class="reference external" href="http://www.osl.iu.edu">Open Systems
|
||||||
|
Lab</a>, University of Hanover <a class="last reference external" href="http://www.ive.uni-hannover.de">Institute for Transport
|
||||||
|
Railway Operation and Construction</a></td></tr>
|
||||||
|
<tr><th class="docinfo-name">Date:</th>
|
||||||
|
<td>2006-09-11</td></tr>
|
||||||
|
<tr><th class="docinfo-name">Copyright:</th>
|
||||||
|
<td>Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003.</td></tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<!-- Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">abstract:</th><td class="field-body"><p class="first">How would you fill up a vector with the numbers zero
|
||||||
|
through one hundred using <tt class="docutils literal"><span class="pre">std::copy()</span></tt>? The only iterator
|
||||||
|
operation missing from builtin integer types is an
|
||||||
|
<tt class="docutils literal"><span class="pre">operator*()</span></tt> that returns the current value of the integer.
|
||||||
|
The counting iterator adaptor adds this crucial piece of
|
||||||
|
functionality to whatever type it wraps. One can use the
|
||||||
|
counting iterator adaptor not only with integer types, but with
|
||||||
|
any incrementable type.</p>
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<p class="last"><tt class="docutils literal"><span class="pre">counting_iterator</span></tt> adapts an object by adding an <tt class="docutils literal"><span class="pre">operator*</span></tt> that
|
||||||
|
returns the current value of the object. All other iterator operations
|
||||||
|
are forwarded to the adapted object.</p>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<div class="contents topic" id="table-of-contents">
|
||||||
|
<p class="topic-title first">Table of Contents</p>
|
||||||
|
<ul class="simple">
|
||||||
|
<li><a class="reference internal" href="#counting-iterator-synopsis" id="id2"><tt class="docutils literal"><span class="pre">counting_iterator</span></tt> synopsis</a></li>
|
||||||
|
<li><a class="reference internal" href="#counting-iterator-requirements" id="id3"><tt class="docutils literal"><span class="pre">counting_iterator</span></tt> requirements</a></li>
|
||||||
|
<li><a class="reference internal" href="#counting-iterator-models" id="id4"><tt class="docutils literal"><span class="pre">counting_iterator</span></tt> models</a></li>
|
||||||
|
<li><a class="reference internal" href="#counting-iterator-operations" id="id5"><tt class="docutils literal"><span class="pre">counting_iterator</span></tt> operations</a></li>
|
||||||
|
<li><a class="reference internal" href="#example" id="id6">Example</a></li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="counting-iterator-synopsis">
|
||||||
|
<h1><a class="toc-backref" href="#id2"><tt class="docutils literal"><span class="pre">counting_iterator</span></tt> synopsis</a></h1>
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<pre class="literal-block">
|
||||||
|
template <
|
||||||
|
class Incrementable
|
||||||
|
, class CategoryOrTraversal = use_default
|
||||||
|
, class Difference = use_default
|
||||||
|
>
|
||||||
|
class counting_iterator
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
typedef Incrementable value_type;
|
||||||
|
typedef const Incrementable& reference;
|
||||||
|
typedef const Incrementable* pointer;
|
||||||
|
typedef /* see below */ difference_type;
|
||||||
|
typedef /* see below */ iterator_category;
|
||||||
|
|
||||||
|
counting_iterator();
|
||||||
|
counting_iterator(counting_iterator const& rhs);
|
||||||
|
explicit counting_iterator(Incrementable x);
|
||||||
|
Incrementable const& base() const;
|
||||||
|
reference operator*() const;
|
||||||
|
counting_iterator& operator++();
|
||||||
|
counting_iterator& operator--();
|
||||||
|
private:
|
||||||
|
Incrementable m_inc; // exposition
|
||||||
|
};
|
||||||
|
</pre>
|
||||||
|
<p>If the <tt class="docutils literal"><span class="pre">Difference</span></tt> argument is <tt class="docutils literal"><span class="pre">use_default</span></tt> then
|
||||||
|
<tt class="docutils literal"><span class="pre">difference_type</span></tt> is an unspecified signed integral
|
||||||
|
type. Otherwise <tt class="docutils literal"><span class="pre">difference_type</span></tt> is <tt class="docutils literal"><span class="pre">Difference</span></tt>.</p>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">iterator_category</span></tt> is determined according to the following
|
||||||
|
algorithm:</p>
|
||||||
|
<pre class="literal-block">
|
||||||
|
if (CategoryOrTraversal is not use_default)
|
||||||
|
return CategoryOrTraversal
|
||||||
|
else if (numeric_limits<Incrementable>::is_specialized)
|
||||||
|
return <a class="reference external" href="iterator_facade.html#iterator-category"><em>iterator-category</em></a>(
|
||||||
|
random_access_traversal_tag, Incrementable, const Incrementable&)
|
||||||
|
else
|
||||||
|
return <a class="reference external" href="iterator_facade.html#iterator-category"><em>iterator-category</em></a>(
|
||||||
|
iterator_traversal<Incrementable>::type,
|
||||||
|
Incrementable, const Incrementable&)
|
||||||
|
</pre>
|
||||||
|
<dl class="docutils">
|
||||||
|
<dt>[<em>Note:</em> implementers are encouraged to provide an implementation of</dt>
|
||||||
|
<dd><tt class="docutils literal"><span class="pre">operator-</span></tt> and a <tt class="docutils literal"><span class="pre">difference_type</span></tt> that avoids overflows in
|
||||||
|
the cases where <tt class="docutils literal"><span class="pre">std::numeric_limits<Incrementable>::is_specialized</span></tt>
|
||||||
|
is true.]</dd>
|
||||||
|
</dl>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="counting-iterator-requirements">
|
||||||
|
<h1><a class="toc-backref" href="#id3"><tt class="docutils literal"><span class="pre">counting_iterator</span></tt> requirements</a></h1>
|
||||||
|
<p>The <tt class="docutils literal"><span class="pre">Incrementable</span></tt> argument shall be Copy Constructible and Assignable.</p>
|
||||||
|
<p>If <tt class="docutils literal"><span class="pre">iterator_category</span></tt> is convertible to <tt class="docutils literal"><span class="pre">forward_iterator_tag</span></tt>
|
||||||
|
or <tt class="docutils literal"><span class="pre">forward_traversal_tag</span></tt>, the following must be well-formed:</p>
|
||||||
|
<pre class="literal-block">
|
||||||
|
Incrementable i, j;
|
||||||
|
++i; // pre-increment
|
||||||
|
i == j; // operator equal
|
||||||
|
</pre>
|
||||||
|
<p>If <tt class="docutils literal"><span class="pre">iterator_category</span></tt> is convertible to
|
||||||
|
<tt class="docutils literal"><span class="pre">bidirectional_iterator_tag</span></tt> or <tt class="docutils literal"><span class="pre">bidirectional_traversal_tag</span></tt>,
|
||||||
|
the following expression must also be well-formed:</p>
|
||||||
|
<pre class="literal-block">
|
||||||
|
--i
|
||||||
|
</pre>
|
||||||
|
<p>If <tt class="docutils literal"><span class="pre">iterator_category</span></tt> is convertible to
|
||||||
|
<tt class="docutils literal"><span class="pre">random_access_iterator_tag</span></tt> or <tt class="docutils literal"><span class="pre">random_access_traversal_tag</span></tt>,
|
||||||
|
the following must must also be valid:</p>
|
||||||
|
<pre class="literal-block">
|
||||||
|
counting_iterator::difference_type n;
|
||||||
|
i += n;
|
||||||
|
n = i - j;
|
||||||
|
i < j;
|
||||||
|
</pre>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="counting-iterator-models">
|
||||||
|
<h1><a class="toc-backref" href="#id4"><tt class="docutils literal"><span class="pre">counting_iterator</span></tt> models</a></h1>
|
||||||
|
<p>Specializations of <tt class="docutils literal"><span class="pre">counting_iterator</span></tt> model Readable Lvalue
|
||||||
|
Iterator. In addition, they model the concepts corresponding to the
|
||||||
|
iterator tags to which their <tt class="docutils literal"><span class="pre">iterator_category</span></tt> is convertible.
|
||||||
|
Also, if <tt class="docutils literal"><span class="pre">CategoryOrTraversal</span></tt> is not <tt class="docutils literal"><span class="pre">use_default</span></tt> then
|
||||||
|
<tt class="docutils literal"><span class="pre">counting_iterator</span></tt> models the concept corresponding to the iterator
|
||||||
|
tag <tt class="docutils literal"><span class="pre">CategoryOrTraversal</span></tt>. Otherwise, if
|
||||||
|
<tt class="docutils literal"><span class="pre">numeric_limits<Incrementable>::is_specialized</span></tt>, then
|
||||||
|
<tt class="docutils literal"><span class="pre">counting_iterator</span></tt> models Random Access Traversal Iterator.
|
||||||
|
Otherwise, <tt class="docutils literal"><span class="pre">counting_iterator</span></tt> models the same iterator traversal
|
||||||
|
concepts modeled by <tt class="docutils literal"><span class="pre">Incrementable</span></tt>.</p>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">counting_iterator<X,C1,D1></span></tt> is interoperable with
|
||||||
|
<tt class="docutils literal"><span class="pre">counting_iterator<Y,C2,D2></span></tt> if and only if <tt class="docutils literal"><span class="pre">X</span></tt> is
|
||||||
|
interoperable with <tt class="docutils literal"><span class="pre">Y</span></tt>.</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="counting-iterator-operations">
|
||||||
|
<h1><a class="toc-backref" href="#id5"><tt class="docutils literal"><span class="pre">counting_iterator</span></tt> operations</a></h1>
|
||||||
|
<p>In addition to the operations required by the concepts modeled by
|
||||||
|
<tt class="docutils literal"><span class="pre">counting_iterator</span></tt>, <tt class="docutils literal"><span class="pre">counting_iterator</span></tt> provides the following
|
||||||
|
operations.</p>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">counting_iterator();</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Requires:</th><td class="field-body"><tt class="docutils literal"><span class="pre">Incrementable</span></tt> is Default Constructible.</td>
|
||||||
|
</tr>
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body">Default construct the member <tt class="docutils literal"><span class="pre">m_inc</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">counting_iterator(counting_iterator</span> <span class="pre">const&</span> <span class="pre">rhs);</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body">Construct member <tt class="docutils literal"><span class="pre">m_inc</span></tt> from <tt class="docutils literal"><span class="pre">rhs.m_inc</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">explicit</span> <span class="pre">counting_iterator(Incrementable</span> <span class="pre">x);</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body">Construct member <tt class="docutils literal"><span class="pre">m_inc</span></tt> from <tt class="docutils literal"><span class="pre">x</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">reference</span> <span class="pre">operator*()</span> <span class="pre">const;</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">m_inc</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">counting_iterator&</span> <span class="pre">operator++();</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body"><tt class="docutils literal"><span class="pre">++m_inc</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">*this</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">counting_iterator&</span> <span class="pre">operator--();</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body"><tt class="docutils literal"><span class="pre">--m_inc</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">*this</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">Incrementable</span> <span class="pre">const&</span> <span class="pre">base()</span> <span class="pre">const;</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">m_inc</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<pre class="literal-block">
|
||||||
|
template <class Incrementable>
|
||||||
|
counting_iterator<Incrementable> make_counting_iterator(Incrementable x);
|
||||||
|
</pre>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body">An instance of <tt class="docutils literal"><span class="pre">counting_iterator<Incrementable></span></tt>
|
||||||
|
with <tt class="docutils literal"><span class="pre">current</span></tt> constructed from <tt class="docutils literal"><span class="pre">x</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
</div>
|
||||||
|
<div class="section" id="example">
|
||||||
|
<h1><a class="toc-backref" href="#id6">Example</a></h1>
|
||||||
|
<p>This example fills an array with numbers and a second array with
|
||||||
|
pointers into the first array, using <tt class="docutils literal"><span class="pre">counting_iterator</span></tt> for both
|
||||||
|
tasks. Finally <tt class="docutils literal"><span class="pre">indirect_iterator</span></tt> is used to print out the numbers
|
||||||
|
into the first array via indirection through the second array.</p>
|
||||||
|
<pre class="literal-block">
|
||||||
|
int N = 7;
|
||||||
|
std::vector<int> numbers;
|
||||||
|
typedef std::vector<int>::iterator n_iter;
|
||||||
|
std::copy(boost::counting_iterator<int>(0),
|
||||||
|
boost::counting_iterator<int>(N),
|
||||||
|
std::back_inserter(numbers));
|
||||||
|
|
||||||
|
std::vector<std::vector<int>::iterator> pointers;
|
||||||
|
std::copy(boost::make_counting_iterator(numbers.begin()),
|
||||||
|
boost::make_counting_iterator(numbers.end()),
|
||||||
|
std::back_inserter(pointers));
|
||||||
|
|
||||||
|
std::cout << "indirectly printing out the numbers from 0 to "
|
||||||
|
<< N << std::endl;
|
||||||
|
std::copy(boost::make_indirect_iterator(pointers.begin()),
|
||||||
|
boost::make_indirect_iterator(pointers.end()),
|
||||||
|
std::ostream_iterator<int>(std::cout, " "));
|
||||||
|
std::cout << std::endl;
|
||||||
|
</pre>
|
||||||
|
<p>The output is:</p>
|
||||||
|
<pre class="literal-block">
|
||||||
|
indirectly printing out the numbers from 0 to 7
|
||||||
|
0 1 2 3 4 5 6
|
||||||
|
</pre>
|
||||||
|
<p>The source code for this example can be found <a class="reference external" href="../example/counting_iterator_example.cpp">here</a>.</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<hr class="footer" />
|
||||||
|
<a class="reference external" href="counting_iterator.rst">View document source</a>.
|
||||||
|
Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
BIN
doc/counting_iterator.pdf
Normal file
BIN
doc/counting_iterator.pdf
Normal file
Binary file not shown.
43
doc/counting_iterator.rst
Normal file
43
doc/counting_iterator.rst
Normal file
@ -0,0 +1,43 @@
|
|||||||
|
.. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
+++++++++++++++++++
|
||||||
|
Counting Iterator
|
||||||
|
+++++++++++++++++++
|
||||||
|
|
||||||
|
:Author: David Abrahams, Jeremy Siek, Thomas Witt
|
||||||
|
:Contact: dave@boost-consulting.com, jsiek@osl.iu.edu, witt@ive.uni-hannover.de
|
||||||
|
:organization: `Boost Consulting`_, Indiana University `Open Systems
|
||||||
|
Lab`_, University of Hanover `Institute for Transport
|
||||||
|
Railway Operation and Construction`_
|
||||||
|
:date: $Date$
|
||||||
|
:copyright: Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003.
|
||||||
|
|
||||||
|
.. _`Boost Consulting`: http://www.boost-consulting.com
|
||||||
|
.. _`Open Systems Lab`: http://www.osl.iu.edu
|
||||||
|
.. _`Institute for Transport Railway Operation and Construction`: http://www.ive.uni-hannover.de
|
||||||
|
|
||||||
|
:abstract: How would you fill up a vector with the numbers zero
|
||||||
|
through one hundred using ``std::copy()``? The only iterator
|
||||||
|
operation missing from builtin integer types is an
|
||||||
|
``operator*()`` that returns the current value of the integer.
|
||||||
|
The counting iterator adaptor adds this crucial piece of
|
||||||
|
functionality to whatever type it wraps. One can use the
|
||||||
|
counting iterator adaptor not only with integer types, but with
|
||||||
|
any incrementable type.
|
||||||
|
|
||||||
|
.. include:: counting_iterator_abstract.rst
|
||||||
|
|
||||||
|
.. contents:: Table of Contents
|
||||||
|
|
||||||
|
``counting_iterator`` synopsis
|
||||||
|
..............................
|
||||||
|
|
||||||
|
.. include:: counting_iterator_ref.rst
|
||||||
|
.. include:: make_counting_iterator.rst
|
||||||
|
|
||||||
|
.. include:: counting_iterator_eg.rst
|
||||||
|
|
||||||
|
.. _iterator-category: iterator_facade.html#iterator-category
|
||||||
|
.. |iterator-category| replace:: *iterator-category*
|
8
doc/counting_iterator_abstract.rst
Normal file
8
doc/counting_iterator_abstract.rst
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
``counting_iterator`` adapts an object by adding an ``operator*`` that
|
||||||
|
returns the current value of the object. All other iterator operations
|
||||||
|
are forwarded to the adapted object.
|
||||||
|
|
43
doc/counting_iterator_eg.rst
Normal file
43
doc/counting_iterator_eg.rst
Normal file
@ -0,0 +1,43 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
Example
|
||||||
|
.......
|
||||||
|
|
||||||
|
This example fills an array with numbers and a second array with
|
||||||
|
pointers into the first array, using ``counting_iterator`` for both
|
||||||
|
tasks. Finally ``indirect_iterator`` is used to print out the numbers
|
||||||
|
into the first array via indirection through the second array.
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
int N = 7;
|
||||||
|
std::vector<int> numbers;
|
||||||
|
typedef std::vector<int>::iterator n_iter;
|
||||||
|
std::copy(boost::counting_iterator<int>(0),
|
||||||
|
boost::counting_iterator<int>(N),
|
||||||
|
std::back_inserter(numbers));
|
||||||
|
|
||||||
|
std::vector<std::vector<int>::iterator> pointers;
|
||||||
|
std::copy(boost::make_counting_iterator(numbers.begin()),
|
||||||
|
boost::make_counting_iterator(numbers.end()),
|
||||||
|
std::back_inserter(pointers));
|
||||||
|
|
||||||
|
std::cout << "indirectly printing out the numbers from 0 to "
|
||||||
|
<< N << std::endl;
|
||||||
|
std::copy(boost::make_indirect_iterator(pointers.begin()),
|
||||||
|
boost::make_indirect_iterator(pointers.end()),
|
||||||
|
std::ostream_iterator<int>(std::cout, " "));
|
||||||
|
std::cout << std::endl;
|
||||||
|
|
||||||
|
|
||||||
|
The output is::
|
||||||
|
|
||||||
|
indirectly printing out the numbers from 0 to 7
|
||||||
|
0 1 2 3 4 5 6
|
||||||
|
|
||||||
|
The source code for this example can be found `here`__.
|
||||||
|
|
||||||
|
__ ../example/counting_iterator_example.cpp
|
||||||
|
|
149
doc/counting_iterator_ref.rst
Normal file
149
doc/counting_iterator_ref.rst
Normal file
@ -0,0 +1,149 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <
|
||||||
|
class Incrementable
|
||||||
|
, class CategoryOrTraversal = use_default
|
||||||
|
, class Difference = use_default
|
||||||
|
>
|
||||||
|
class counting_iterator
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
typedef Incrementable value_type;
|
||||||
|
typedef const Incrementable& reference;
|
||||||
|
typedef const Incrementable* pointer;
|
||||||
|
typedef /* see below */ difference_type;
|
||||||
|
typedef /* see below */ iterator_category;
|
||||||
|
|
||||||
|
counting_iterator();
|
||||||
|
counting_iterator(counting_iterator const& rhs);
|
||||||
|
explicit counting_iterator(Incrementable x);
|
||||||
|
Incrementable const& base() const;
|
||||||
|
reference operator*() const;
|
||||||
|
counting_iterator& operator++();
|
||||||
|
counting_iterator& operator--();
|
||||||
|
private:
|
||||||
|
Incrementable m_inc; // exposition
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
If the ``Difference`` argument is ``use_default`` then
|
||||||
|
``difference_type`` is an unspecified signed integral
|
||||||
|
type. Otherwise ``difference_type`` is ``Difference``.
|
||||||
|
|
||||||
|
``iterator_category`` is determined according to the following
|
||||||
|
algorithm:
|
||||||
|
|
||||||
|
.. parsed-literal::
|
||||||
|
|
||||||
|
if (CategoryOrTraversal is not use_default)
|
||||||
|
return CategoryOrTraversal
|
||||||
|
else if (numeric_limits<Incrementable>::is_specialized)
|
||||||
|
return |iterator-category|_\ (
|
||||||
|
random_access_traversal_tag, Incrementable, const Incrementable&)
|
||||||
|
else
|
||||||
|
return |iterator-category|_\ (
|
||||||
|
iterator_traversal<Incrementable>::type,
|
||||||
|
Incrementable, const Incrementable&)
|
||||||
|
|
||||||
|
[*Note:* implementers are encouraged to provide an implementation of
|
||||||
|
``operator-`` and a ``difference_type`` that avoids overflows in
|
||||||
|
the cases where ``std::numeric_limits<Incrementable>::is_specialized``
|
||||||
|
is true.]
|
||||||
|
|
||||||
|
``counting_iterator`` requirements
|
||||||
|
..................................
|
||||||
|
|
||||||
|
The ``Incrementable`` argument shall be Copy Constructible and Assignable.
|
||||||
|
|
||||||
|
If ``iterator_category`` is convertible to ``forward_iterator_tag``
|
||||||
|
or ``forward_traversal_tag``, the following must be well-formed::
|
||||||
|
|
||||||
|
Incrementable i, j;
|
||||||
|
++i; // pre-increment
|
||||||
|
i == j; // operator equal
|
||||||
|
|
||||||
|
|
||||||
|
If ``iterator_category`` is convertible to
|
||||||
|
``bidirectional_iterator_tag`` or ``bidirectional_traversal_tag``,
|
||||||
|
the following expression must also be well-formed::
|
||||||
|
|
||||||
|
--i
|
||||||
|
|
||||||
|
If ``iterator_category`` is convertible to
|
||||||
|
``random_access_iterator_tag`` or ``random_access_traversal_tag``,
|
||||||
|
the following must must also be valid::
|
||||||
|
|
||||||
|
counting_iterator::difference_type n;
|
||||||
|
i += n;
|
||||||
|
n = i - j;
|
||||||
|
i < j;
|
||||||
|
|
||||||
|
``counting_iterator`` models
|
||||||
|
............................
|
||||||
|
|
||||||
|
Specializations of ``counting_iterator`` model Readable Lvalue
|
||||||
|
Iterator. In addition, they model the concepts corresponding to the
|
||||||
|
iterator tags to which their ``iterator_category`` is convertible.
|
||||||
|
Also, if ``CategoryOrTraversal`` is not ``use_default`` then
|
||||||
|
``counting_iterator`` models the concept corresponding to the iterator
|
||||||
|
tag ``CategoryOrTraversal``. Otherwise, if
|
||||||
|
``numeric_limits<Incrementable>::is_specialized``, then
|
||||||
|
``counting_iterator`` models Random Access Traversal Iterator.
|
||||||
|
Otherwise, ``counting_iterator`` models the same iterator traversal
|
||||||
|
concepts modeled by ``Incrementable``.
|
||||||
|
|
||||||
|
``counting_iterator<X,C1,D1>`` is interoperable with
|
||||||
|
``counting_iterator<Y,C2,D2>`` if and only if ``X`` is
|
||||||
|
interoperable with ``Y``.
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
``counting_iterator`` operations
|
||||||
|
................................
|
||||||
|
|
||||||
|
In addition to the operations required by the concepts modeled by
|
||||||
|
``counting_iterator``, ``counting_iterator`` provides the following
|
||||||
|
operations.
|
||||||
|
|
||||||
|
|
||||||
|
``counting_iterator();``
|
||||||
|
|
||||||
|
:Requires: ``Incrementable`` is Default Constructible.
|
||||||
|
:Effects: Default construct the member ``m_inc``.
|
||||||
|
|
||||||
|
|
||||||
|
``counting_iterator(counting_iterator const& rhs);``
|
||||||
|
|
||||||
|
:Effects: Construct member ``m_inc`` from ``rhs.m_inc``.
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
``explicit counting_iterator(Incrementable x);``
|
||||||
|
|
||||||
|
:Effects: Construct member ``m_inc`` from ``x``.
|
||||||
|
|
||||||
|
|
||||||
|
``reference operator*() const;``
|
||||||
|
|
||||||
|
:Returns: ``m_inc``
|
||||||
|
|
||||||
|
|
||||||
|
``counting_iterator& operator++();``
|
||||||
|
|
||||||
|
:Effects: ``++m_inc``
|
||||||
|
:Returns: ``*this``
|
||||||
|
|
||||||
|
|
||||||
|
``counting_iterator& operator--();``
|
||||||
|
|
||||||
|
:Effects: ``--m_inc``
|
||||||
|
:Returns: ``*this``
|
||||||
|
|
||||||
|
|
||||||
|
``Incrementable const& base() const;``
|
||||||
|
|
||||||
|
:Returns: ``m_inc``
|
226
doc/default.css
Normal file
226
doc/default.css
Normal file
@ -0,0 +1,226 @@
|
|||||||
|
/*
|
||||||
|
:Author: David Goodger
|
||||||
|
:Contact: goodger@users.sourceforge.net
|
||||||
|
:date: $Date$
|
||||||
|
:version: $Revision$
|
||||||
|
:copyright: This stylesheet has been placed in the public domain.
|
||||||
|
|
||||||
|
boostinspect:nolicense
|
||||||
|
|
||||||
|
Default cascading style sheet for the HTML output of Docutils.
|
||||||
|
*/
|
||||||
|
|
||||||
|
.first {
|
||||||
|
margin-top: 0 }
|
||||||
|
|
||||||
|
.last {
|
||||||
|
margin-bottom: 0 }
|
||||||
|
|
||||||
|
a.toc-backref {
|
||||||
|
text-decoration: none ;
|
||||||
|
color: black }
|
||||||
|
|
||||||
|
dd {
|
||||||
|
margin-bottom: 0.5em }
|
||||||
|
|
||||||
|
div.abstract {
|
||||||
|
margin: 2em 5em }
|
||||||
|
|
||||||
|
div.abstract p.topic-title {
|
||||||
|
font-weight: bold ;
|
||||||
|
text-align: center }
|
||||||
|
|
||||||
|
div.attention, div.caution, div.danger, div.error, div.hint,
|
||||||
|
div.important, div.note, div.tip, div.warning, div.admonition {
|
||||||
|
margin: 2em ;
|
||||||
|
border: medium outset ;
|
||||||
|
padding: 1em }
|
||||||
|
|
||||||
|
div.attention p.admonition-title, div.caution p.admonition-title,
|
||||||
|
div.danger p.admonition-title, div.error p.admonition-title,
|
||||||
|
div.warning p.admonition-title {
|
||||||
|
color: red ;
|
||||||
|
font-weight: bold ;
|
||||||
|
font-family: sans-serif }
|
||||||
|
|
||||||
|
div.hint p.admonition-title, div.important p.admonition-title,
|
||||||
|
div.note p.admonition-title, div.tip p.admonition-title,
|
||||||
|
div.admonition p.admonition-title {
|
||||||
|
font-weight: bold ;
|
||||||
|
font-family: sans-serif }
|
||||||
|
|
||||||
|
div.dedication {
|
||||||
|
margin: 2em 5em ;
|
||||||
|
text-align: center ;
|
||||||
|
font-style: italic }
|
||||||
|
|
||||||
|
div.dedication p.topic-title {
|
||||||
|
font-weight: bold ;
|
||||||
|
font-style: normal }
|
||||||
|
|
||||||
|
div.figure {
|
||||||
|
margin-left: 2em }
|
||||||
|
|
||||||
|
div.footer, div.header {
|
||||||
|
font-size: smaller }
|
||||||
|
|
||||||
|
div.sidebar {
|
||||||
|
margin-left: 1em ;
|
||||||
|
border: medium outset ;
|
||||||
|
padding: 0em 1em ;
|
||||||
|
background-color: #ffffee ;
|
||||||
|
width: 40% ;
|
||||||
|
float: right ;
|
||||||
|
clear: right }
|
||||||
|
|
||||||
|
div.sidebar p.rubric {
|
||||||
|
font-family: sans-serif ;
|
||||||
|
font-size: medium }
|
||||||
|
|
||||||
|
div.system-messages {
|
||||||
|
margin: 5em }
|
||||||
|
|
||||||
|
div.system-messages h1 {
|
||||||
|
color: red }
|
||||||
|
|
||||||
|
div.system-message {
|
||||||
|
border: medium outset ;
|
||||||
|
padding: 1em }
|
||||||
|
|
||||||
|
div.system-message p.system-message-title {
|
||||||
|
color: red ;
|
||||||
|
font-weight: bold }
|
||||||
|
|
||||||
|
div.topic {
|
||||||
|
margin: 2em }
|
||||||
|
|
||||||
|
h1.title {
|
||||||
|
text-align: center }
|
||||||
|
|
||||||
|
h2.subtitle {
|
||||||
|
text-align: center }
|
||||||
|
|
||||||
|
hr {
|
||||||
|
width: 75% }
|
||||||
|
|
||||||
|
ol.simple, ul.simple {
|
||||||
|
margin-bottom: 1em }
|
||||||
|
|
||||||
|
ol.arabic {
|
||||||
|
list-style: decimal }
|
||||||
|
|
||||||
|
ol.loweralpha {
|
||||||
|
list-style: lower-alpha }
|
||||||
|
|
||||||
|
ol.upperalpha {
|
||||||
|
list-style: upper-alpha }
|
||||||
|
|
||||||
|
ol.lowerroman {
|
||||||
|
list-style: lower-roman }
|
||||||
|
|
||||||
|
ol.upperroman {
|
||||||
|
list-style: upper-roman }
|
||||||
|
|
||||||
|
p.attribution {
|
||||||
|
text-align: right ;
|
||||||
|
margin-left: 50% }
|
||||||
|
|
||||||
|
p.caption {
|
||||||
|
font-style: italic }
|
||||||
|
|
||||||
|
p.credits {
|
||||||
|
font-style: italic ;
|
||||||
|
font-size: smaller }
|
||||||
|
|
||||||
|
p.label {
|
||||||
|
white-space: nowrap }
|
||||||
|
|
||||||
|
p.rubric {
|
||||||
|
font-weight: bold ;
|
||||||
|
font-size: larger ;
|
||||||
|
color: maroon ;
|
||||||
|
text-align: center }
|
||||||
|
|
||||||
|
p.sidebar-title {
|
||||||
|
font-family: sans-serif ;
|
||||||
|
font-weight: bold ;
|
||||||
|
font-size: larger }
|
||||||
|
|
||||||
|
p.sidebar-subtitle {
|
||||||
|
font-family: sans-serif ;
|
||||||
|
font-weight: bold }
|
||||||
|
|
||||||
|
p.topic-title {
|
||||||
|
font-weight: bold }
|
||||||
|
|
||||||
|
pre.address {
|
||||||
|
margin-bottom: 0 ;
|
||||||
|
margin-top: 0 ;
|
||||||
|
font-family: serif ;
|
||||||
|
font-size: 100% }
|
||||||
|
|
||||||
|
pre.line-block {
|
||||||
|
font-family: serif ;
|
||||||
|
font-size: 100% }
|
||||||
|
|
||||||
|
pre.literal-block, pre.doctest-block {
|
||||||
|
margin-left: 2em ;
|
||||||
|
margin-right: 2em ;
|
||||||
|
background-color: #eeeeee }
|
||||||
|
|
||||||
|
span.classifier {
|
||||||
|
font-family: sans-serif ;
|
||||||
|
font-style: oblique }
|
||||||
|
|
||||||
|
span.classifier-delimiter {
|
||||||
|
font-family: sans-serif ;
|
||||||
|
font-weight: bold }
|
||||||
|
|
||||||
|
span.interpreted {
|
||||||
|
font-family: sans-serif }
|
||||||
|
|
||||||
|
span.option {
|
||||||
|
white-space: nowrap }
|
||||||
|
|
||||||
|
span.option-argument {
|
||||||
|
font-style: italic }
|
||||||
|
|
||||||
|
span.pre {
|
||||||
|
white-space: pre }
|
||||||
|
|
||||||
|
span.problematic {
|
||||||
|
color: red }
|
||||||
|
|
||||||
|
table {
|
||||||
|
margin-top: 0.5em ;
|
||||||
|
margin-bottom: 0.5em }
|
||||||
|
|
||||||
|
table.citation {
|
||||||
|
border-left: solid thin gray ;
|
||||||
|
padding-left: 0.5ex }
|
||||||
|
|
||||||
|
table.docinfo {
|
||||||
|
margin: 2em 4em }
|
||||||
|
|
||||||
|
table.footnote {
|
||||||
|
border-left: solid thin black ;
|
||||||
|
padding-left: 0.5ex }
|
||||||
|
|
||||||
|
td, th {
|
||||||
|
padding-left: 0.5em ;
|
||||||
|
padding-right: 0.5em ;
|
||||||
|
vertical-align: top }
|
||||||
|
|
||||||
|
th.docinfo-name, th.field-name {
|
||||||
|
font-weight: bold ;
|
||||||
|
text-align: left ;
|
||||||
|
white-space: nowrap }
|
||||||
|
|
||||||
|
h1 tt, h2 tt, h3 tt, h4 tt, h5 tt, h6 tt {
|
||||||
|
font-size: 100% }
|
||||||
|
|
||||||
|
tt {
|
||||||
|
background-color: #eeeeee }
|
||||||
|
|
||||||
|
ul.auto-toc {
|
||||||
|
list-style-type: none }
|
54
doc/docutils.sty
Normal file
54
doc/docutils.sty
Normal file
@ -0,0 +1,54 @@
|
|||||||
|
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
||||||
|
%%%%%%%%%%%%%% docutils.sty: A style for docutils latex output %%%%%%%%%%%%%%%
|
||||||
|
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
||||||
|
%%
|
||||||
|
%% o author: Alexander Schmolck (a.schmolck@gmx.net)
|
||||||
|
%% o created: 2002-07-07 10:50:31+00:40
|
||||||
|
%% o last modified: $Date: 2004/01/29 05:55:26 $
|
||||||
|
%% o keywords:
|
||||||
|
%% o license:
|
||||||
|
%XXX titlesec
|
||||||
|
%% XXX geometry
|
||||||
|
\usepackage{graphicx}
|
||||||
|
\usepackage{latexsym} % extra symbols
|
||||||
|
\usepackage{url} % !!!: pay attention when using in other commands!!!
|
||||||
|
\usepackage{verbatim} % normal verbatim has lenght-limit
|
||||||
|
\usepackage{enumerate} % easy style choice with e.g: ``\begin{enumerate}[Ex i.]``
|
||||||
|
\usepackage{hyperref} %href, htarget and hlink XXX: pdfauthor, pdfcreator etc.
|
||||||
|
\usepackage{xr} %XXX do we need this?
|
||||||
|
% need this to have ``fboxes`` in ``enviroments``, as well as ``verbatim``s
|
||||||
|
\usepackage{fancybox}
|
||||||
|
\usepackage{mdwtab} % better tables and arrays (fixes spacing and adds
|
||||||
|
% vertical align and multirows (m))
|
||||||
|
\usepackage{ltxtable} % long and autoscaling tables (use X for autoscaled
|
||||||
|
% columns)
|
||||||
|
\newcommand{\transition}{\vspace{2em}\par\hrule{}\par\vspace{2em}}
|
||||||
|
\newcommand{\classifier}[1]{(\textit{#1})}
|
||||||
|
\newenvironment{topic}[1]%
|
||||||
|
{\begin{Sbox}%
|
||||||
|
\begin{minipage}{.8\textwidth}%
|
||||||
|
\protect{\large{\textbf{#1}}}\par\vspace{.5em}}%
|
||||||
|
{\end{minipage}\end{Sbox}\fbox{\TheSbox}\par\vspace{.5em}}
|
||||||
|
%XXX shadow box for warnings?
|
||||||
|
\newenvironment{admonition}[1]%
|
||||||
|
{\begin{center}%
|
||||||
|
\begin{Sbox}%
|
||||||
|
\begin{minipage}{.9\textwidth}%
|
||||||
|
\protect{\textsc{#1}}\par\vspace{.2em}}%
|
||||||
|
{\end{minipage}\end{Sbox}\fbox{\TheSbox}\par\vspace{.5em}\end{center}}
|
||||||
|
|
||||||
|
\newenvironment{doctest}%
|
||||||
|
{\VerbatimEnvironment
|
||||||
|
\begin{Verbatim}}%
|
||||||
|
{\end{Verbatim}}
|
||||||
|
% {%
|
||||||
|
% \begin{Sbox}%
|
||||||
|
% \begin{minipage}{.8\textwidth}%
|
||||||
|
% \protect{\large{\textsc{#1}}\par\vspace{.5em}}}%
|
||||||
|
% {\end{minipage}\end{Sbox}\fbox{\TheSbox}\par\vspace{.5em}}
|
||||||
|
%{\end{minipage}\end{Sbox}\fbox{\TheSbox}}
|
||||||
|
|
||||||
|
|
||||||
|
%% just a piece of example code
|
||||||
|
% \newcommand{\vitem}%
|
||||||
|
% {\SaveVerb[{\item[\UseVerb{\MyTemp}]}]{\MyTemp}}
|
2716
doc/facade-and-adaptor.html
Normal file
2716
doc/facade-and-adaptor.html
Normal file
File diff suppressed because it is too large
Load Diff
BIN
doc/facade-and-adaptor.pdf
Normal file
BIN
doc/facade-and-adaptor.pdf
Normal file
Binary file not shown.
438
doc/facade-and-adaptor.rst
Normal file
438
doc/facade-and-adaptor.rst
Normal file
@ -0,0 +1,438 @@
|
|||||||
|
.. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
+++++++++++++++++++++++++++++
|
||||||
|
Iterator Facade and Adaptor
|
||||||
|
+++++++++++++++++++++++++++++
|
||||||
|
|
||||||
|
:Author: David Abrahams, Jeremy Siek, Thomas Witt
|
||||||
|
:Contact: dave@boost-consulting.com, jsiek@osl.iu.edu, witt@styleadvisor.com
|
||||||
|
:organization: `Boost Consulting`_, Indiana University `Open Systems
|
||||||
|
Lab`_, `Zephyr Associates, Inc.`_
|
||||||
|
:date: $Date$
|
||||||
|
|
||||||
|
:Number: This is a revised version of N1530_\ =03-0113, which was
|
||||||
|
accepted for Technical Report 1 by the C++ standard
|
||||||
|
committee's library working group.
|
||||||
|
|
||||||
|
.. Version 1.9 of this ReStructuredText document corresponds to
|
||||||
|
n1530_, the paper accepted by the LWG.
|
||||||
|
|
||||||
|
.. _n1530: http://anubis.dkuug.dk/jtc1/sc22/wg21/docs/papers/2003/n1530.html
|
||||||
|
|
||||||
|
:copyright: Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003.
|
||||||
|
|
||||||
|
.. _`Boost Consulting`: http://www.boost-consulting.com
|
||||||
|
.. _`Open Systems Lab`: http://www.osl.iu.edu
|
||||||
|
.. _`Zephyr Associates, Inc.`: http://www.styleadvisor.com
|
||||||
|
|
||||||
|
:abstract: We propose a set of class templates that help programmers
|
||||||
|
build standard-conforming iterators, both from scratch and
|
||||||
|
by adapting other iterators.
|
||||||
|
|
||||||
|
.. contents:: Table of Contents
|
||||||
|
|
||||||
|
============
|
||||||
|
Motivation
|
||||||
|
============
|
||||||
|
|
||||||
|
Iterators play an important role in modern C++ programming. The
|
||||||
|
iterator is the central abstraction of the algorithms of the Standard
|
||||||
|
Library, allowing algorithms to be re-used in in a wide variety of
|
||||||
|
contexts. The C++ Standard Library contains a wide variety of useful
|
||||||
|
iterators. Every one of the standard containers comes with constant
|
||||||
|
and mutable iterators [#mutable]_, and also reverse versions of those
|
||||||
|
same iterators which traverse the container in the opposite direction.
|
||||||
|
The Standard also supplies ``istream_iterator`` and
|
||||||
|
``ostream_iterator`` for reading from and writing to streams,
|
||||||
|
``insert_iterator``, ``front_insert_iterator`` and
|
||||||
|
``back_insert_iterator`` for inserting elements into containers, and
|
||||||
|
``raw_storage_iterator`` for initializing raw memory [7].
|
||||||
|
|
||||||
|
Despite the many iterators supplied by the Standard Library, obvious
|
||||||
|
and useful iterators are missing, and creating new iterator types is
|
||||||
|
still a common task for C++ programmers. The literature documents
|
||||||
|
several of these, for example line_iterator [3] and Constant_iterator
|
||||||
|
[9]. The iterator abstraction is so powerful that we expect
|
||||||
|
programmers will always need to invent new iterator types.
|
||||||
|
|
||||||
|
Although it is easy to create iterators that *almost* conform to the
|
||||||
|
standard, the iterator requirements contain subtleties which can make
|
||||||
|
creating an iterator which *actually* conforms quite difficult.
|
||||||
|
Further, the iterator interface is rich, containing many operators
|
||||||
|
that are technically redundant and tedious to implement. To automate
|
||||||
|
the repetitive work of constructing iterators, we propose
|
||||||
|
``iterator_facade``, an iterator base class template which provides
|
||||||
|
the rich interface of standard iterators and delegates its
|
||||||
|
implementation to member functions of the derived class. In addition
|
||||||
|
to reducing the amount of code necessary to create an iterator, the
|
||||||
|
``iterator_facade`` also provides compile-time error detection.
|
||||||
|
Iterator implementation mistakes that often go unnoticed are turned
|
||||||
|
into compile-time errors because the derived class implementation must
|
||||||
|
match the expectations of the ``iterator_facade``.
|
||||||
|
|
||||||
|
A common pattern of iterator construction is the adaptation of one
|
||||||
|
iterator to form a new one. The functionality of an iterator is
|
||||||
|
composed of four orthogonal aspects: traversal, indirection, equality
|
||||||
|
comparison and distance measurement. Adapting an old iterator to
|
||||||
|
create a new one often saves work because one can reuse one aspect of
|
||||||
|
functionality while redefining the other. For example, the Standard
|
||||||
|
provides ``reverse_iterator``, which adapts any Bidirectional Iterator
|
||||||
|
by inverting its direction of traversal. As with plain iterators,
|
||||||
|
iterator adaptors defined outside the Standard have become commonplace
|
||||||
|
in the literature:
|
||||||
|
|
||||||
|
* Checked iter[13] adds bounds-checking to an existing iterator.
|
||||||
|
|
||||||
|
* The iterators of the View Template Library[14], which adapts
|
||||||
|
containers, are themselves adaptors over the underlying iterators.
|
||||||
|
|
||||||
|
* Smart iterators [5] adapt an iterator's dereferencing behavior by
|
||||||
|
applying a function object to the object being referenced and
|
||||||
|
returning the result.
|
||||||
|
|
||||||
|
* Custom iterators [4], in which a variety of adaptor types are enumerated.
|
||||||
|
|
||||||
|
* Compound iterators [1], which access a slice out of a container of containers.
|
||||||
|
|
||||||
|
* Several iterator adaptors from the MTL [12]. The MTL contains a
|
||||||
|
strided iterator, where each call to ``operator++()`` moves the
|
||||||
|
iterator ahead by some constant factor, and a scaled iterator, which
|
||||||
|
multiplies the dereferenced value by some constant.
|
||||||
|
|
||||||
|
.. [#concept] We use the term concept to mean a set of requirements
|
||||||
|
that a type must satisfy to be used with a particular template
|
||||||
|
parameter.
|
||||||
|
|
||||||
|
.. [#mutable] The term mutable iterator refers to iterators over objects that
|
||||||
|
can be changed by assigning to the dereferenced iterator, while
|
||||||
|
constant iterator refers to iterators over objects that cannot be
|
||||||
|
modified.
|
||||||
|
|
||||||
|
To fulfill the need for constructing adaptors, we propose the
|
||||||
|
``iterator_adaptor`` class template. Instantiations of
|
||||||
|
``iterator_adaptor`` serve as a base classes for new iterators,
|
||||||
|
providing the default behavior of forwarding all operations to the
|
||||||
|
underlying iterator. The user can selectively replace these features
|
||||||
|
in the derived iterator class. This proposal also includes a number
|
||||||
|
of more specialized adaptors, such as the ``transform_iterator`` that
|
||||||
|
applies some user-specified function during the dereference of the
|
||||||
|
iterator.
|
||||||
|
|
||||||
|
========================
|
||||||
|
Impact on the Standard
|
||||||
|
========================
|
||||||
|
|
||||||
|
This proposal is purely an addition to the C++ standard library.
|
||||||
|
However, note that this proposal relies on the proposal for New
|
||||||
|
Iterator Concepts.
|
||||||
|
|
||||||
|
========
|
||||||
|
Design
|
||||||
|
========
|
||||||
|
|
||||||
|
Iterator Concepts
|
||||||
|
=================
|
||||||
|
|
||||||
|
This proposal is formulated in terms of the new ``iterator concepts``
|
||||||
|
as proposed in n1550_, since user-defined and especially adapted
|
||||||
|
iterators suffer from the well known categorization problems that are
|
||||||
|
inherent to the current iterator categories.
|
||||||
|
|
||||||
|
.. _n1550: http://anubis.dkuug.dk/JTC1/SC22/WG21/docs/papers/2003/n1550.html
|
||||||
|
|
||||||
|
This proposal does not strictly depend on proposal n1550_, as there
|
||||||
|
is a direct mapping between new and old categories. This proposal
|
||||||
|
could be reformulated using this mapping if n1550_ was not accepted.
|
||||||
|
|
||||||
|
Interoperability
|
||||||
|
================
|
||||||
|
|
||||||
|
The question of iterator interoperability is poorly addressed in the
|
||||||
|
current standard. There are currently two defect reports that are
|
||||||
|
concerned with interoperability issues.
|
||||||
|
|
||||||
|
Issue 179_ concerns the fact that mutable container iterator types
|
||||||
|
are only required to be convertible to the corresponding constant
|
||||||
|
iterator types, but objects of these types are not required to
|
||||||
|
interoperate in comparison or subtraction expressions. This situation
|
||||||
|
is tedious in practice and out of line with the way built in types
|
||||||
|
work. This proposal implements the proposed resolution to issue
|
||||||
|
179_, as most standard library implementations do nowadays. In other
|
||||||
|
words, if an iterator type A has an implicit or user defined
|
||||||
|
conversion to an iterator type B, the iterator types are interoperable
|
||||||
|
and the usual set of operators are available.
|
||||||
|
|
||||||
|
Issue 280_ concerns the current lack of interoperability between
|
||||||
|
reverse iterator types. The proposed new reverse_iterator template
|
||||||
|
fixes the issues raised in 280. It provides the desired
|
||||||
|
interoperability without introducing unwanted overloads.
|
||||||
|
|
||||||
|
.. _179: http://anubis.dkuug.dk/jtc1/sc22/wg21/docs/lwg-defects.html#179
|
||||||
|
.. _280: http://anubis.dkuug.dk/jtc1/sc22/wg21/docs/lwg-active.html#280
|
||||||
|
|
||||||
|
|
||||||
|
Iterator Facade
|
||||||
|
===============
|
||||||
|
|
||||||
|
.. include:: iterator_facade_body.rst
|
||||||
|
|
||||||
|
Iterator Adaptor
|
||||||
|
================
|
||||||
|
|
||||||
|
.. include:: iterator_adaptor_body.rst
|
||||||
|
|
||||||
|
Specialized Adaptors
|
||||||
|
====================
|
||||||
|
|
||||||
|
This proposal also contains several examples of specialized adaptors
|
||||||
|
which were easily implemented using ``iterator_adaptor``:
|
||||||
|
|
||||||
|
* ``indirect_iterator``, which iterates over iterators, pointers,
|
||||||
|
or smart pointers and applies an extra level of dereferencing.
|
||||||
|
|
||||||
|
* A new ``reverse_iterator``, which inverts the direction of a Base
|
||||||
|
iterator's motion, while allowing adapted constant and mutable
|
||||||
|
iterators to interact in the expected ways (unlike those in most
|
||||||
|
implementations of C++98).
|
||||||
|
|
||||||
|
* ``transform_iterator``, which applies a user-defined function object
|
||||||
|
to the underlying values when dereferenced.
|
||||||
|
|
||||||
|
* ``filter_iterator``, which provides a view of an iterator range in
|
||||||
|
which some elements of the underlying range are skipped.
|
||||||
|
|
||||||
|
.. _counting:
|
||||||
|
|
||||||
|
* ``counting_iterator``, which adapts any incrementable type
|
||||||
|
(e.g. integers, iterators) so that incrementing/decrementing the
|
||||||
|
adapted iterator and dereferencing it produces successive values of
|
||||||
|
the Base type.
|
||||||
|
|
||||||
|
* ``function_output_iterator``, which makes it easier to create custom
|
||||||
|
output iterators.
|
||||||
|
|
||||||
|
Based on examples in the Boost library, users have generated many new
|
||||||
|
adaptors, among them a permutation adaptor which applies some
|
||||||
|
permutation to a random access iterator, and a strided adaptor, which
|
||||||
|
adapts a random access iterator by multiplying its unit of motion by a
|
||||||
|
constant factor. In addition, the Boost Graph Library (BGL) uses
|
||||||
|
iterator adaptors to adapt other graph libraries, such as LEDA [10]
|
||||||
|
and Stanford GraphBase [8], to the BGL interface (which requires C++
|
||||||
|
Standard compliant iterators).
|
||||||
|
|
||||||
|
===============
|
||||||
|
Proposed Text
|
||||||
|
===============
|
||||||
|
|
||||||
|
|
||||||
|
Header ``<iterator_helper>`` synopsis [lib.iterator.helper.synopsis]
|
||||||
|
=======================================================================
|
||||||
|
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
struct use_default;
|
||||||
|
|
||||||
|
struct iterator_core_access { /* implementation detail */ };
|
||||||
|
|
||||||
|
template <
|
||||||
|
class Derived
|
||||||
|
, class Value
|
||||||
|
, class CategoryOrTraversal
|
||||||
|
, class Reference = Value&
|
||||||
|
, class Difference = ptrdiff_t
|
||||||
|
>
|
||||||
|
class iterator_facade;
|
||||||
|
|
||||||
|
template <
|
||||||
|
class Derived
|
||||||
|
, class Base
|
||||||
|
, class Value = use_default
|
||||||
|
, class CategoryOrTraversal = use_default
|
||||||
|
, class Reference = use_default
|
||||||
|
, class Difference = use_default
|
||||||
|
>
|
||||||
|
class iterator_adaptor;
|
||||||
|
|
||||||
|
template <
|
||||||
|
class Iterator
|
||||||
|
, class Value = use_default
|
||||||
|
, class CategoryOrTraversal = use_default
|
||||||
|
, class Reference = use_default
|
||||||
|
, class Difference = use_default
|
||||||
|
>
|
||||||
|
class indirect_iterator;
|
||||||
|
|
||||||
|
template <class Dereferenceable>
|
||||||
|
struct pointee;
|
||||||
|
|
||||||
|
template <class Dereferenceable>
|
||||||
|
struct indirect_reference;
|
||||||
|
|
||||||
|
template <class Iterator>
|
||||||
|
class reverse_iterator;
|
||||||
|
|
||||||
|
template <
|
||||||
|
class UnaryFunction
|
||||||
|
, class Iterator
|
||||||
|
, class Reference = use_default
|
||||||
|
, class Value = use_default
|
||||||
|
>
|
||||||
|
class transform_iterator;
|
||||||
|
|
||||||
|
template <class Predicate, class Iterator>
|
||||||
|
class filter_iterator;
|
||||||
|
|
||||||
|
template <
|
||||||
|
class Incrementable
|
||||||
|
, class CategoryOrTraversal = use_default
|
||||||
|
, class Difference = use_default
|
||||||
|
>
|
||||||
|
class counting_iterator;
|
||||||
|
|
||||||
|
template <class UnaryFunction>
|
||||||
|
class function_output_iterator;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
Iterator facade [lib.iterator.facade]
|
||||||
|
=====================================
|
||||||
|
|
||||||
|
.. include:: iterator_facade_abstract.rst
|
||||||
|
|
||||||
|
Class template ``iterator_facade``
|
||||||
|
----------------------------------
|
||||||
|
|
||||||
|
.. include:: iterator_facade_ref.rst
|
||||||
|
|
||||||
|
Iterator adaptor [lib.iterator.adaptor]
|
||||||
|
=======================================
|
||||||
|
|
||||||
|
.. include:: iterator_adaptor_abstract.rst
|
||||||
|
|
||||||
|
Class template ``iterator_adaptor``
|
||||||
|
-----------------------------------
|
||||||
|
|
||||||
|
.. include:: iterator_adaptor_ref.rst
|
||||||
|
|
||||||
|
|
||||||
|
Specialized adaptors [lib.iterator.special.adaptors]
|
||||||
|
====================================================
|
||||||
|
|
||||||
|
|
||||||
|
The ``enable_if_convertible<X,Y>::type`` expression used in
|
||||||
|
this section is for exposition purposes. The converting constructors
|
||||||
|
for specialized adaptors should be only be in an overload set provided
|
||||||
|
that an object of type ``X`` is implicitly convertible to an object of
|
||||||
|
type ``Y``.
|
||||||
|
The signatures involving ``enable_if_convertible`` should behave
|
||||||
|
*as-if* ``enable_if_convertible`` were defined to be::
|
||||||
|
|
||||||
|
template <bool> enable_if_convertible_impl
|
||||||
|
{};
|
||||||
|
|
||||||
|
template <> enable_if_convertible_impl<true>
|
||||||
|
{ struct type; };
|
||||||
|
|
||||||
|
template<typename From, typename To>
|
||||||
|
struct enable_if_convertible
|
||||||
|
: enable_if_convertible_impl<is_convertible<From,To>::value>
|
||||||
|
{};
|
||||||
|
|
||||||
|
If an expression other than the default argument is used to supply
|
||||||
|
the value of a function parameter whose type is written in terms
|
||||||
|
of ``enable_if_convertible``, the program is ill-formed, no
|
||||||
|
diagnostic required.
|
||||||
|
|
||||||
|
[*Note:* The ``enable_if_convertible`` approach uses SFINAE to
|
||||||
|
take the constructor out of the overload set when the types are not
|
||||||
|
implicitly convertible.
|
||||||
|
]
|
||||||
|
|
||||||
|
|
||||||
|
Indirect iterator
|
||||||
|
-----------------
|
||||||
|
|
||||||
|
.. include:: indirect_iterator_abstract.rst
|
||||||
|
|
||||||
|
Class template ``pointee``
|
||||||
|
....................................
|
||||||
|
|
||||||
|
.. include:: pointee_ref.rst
|
||||||
|
|
||||||
|
Class template ``indirect_reference``
|
||||||
|
.....................................
|
||||||
|
|
||||||
|
.. include:: indirect_reference_ref.rst
|
||||||
|
|
||||||
|
Class template ``indirect_iterator``
|
||||||
|
....................................
|
||||||
|
|
||||||
|
.. include:: indirect_iterator_ref.rst
|
||||||
|
|
||||||
|
Reverse iterator
|
||||||
|
----------------
|
||||||
|
|
||||||
|
.. include:: reverse_iterator_abstract.rst
|
||||||
|
|
||||||
|
Class template ``reverse_iterator``
|
||||||
|
...................................
|
||||||
|
|
||||||
|
.. include:: reverse_iterator_ref.rst
|
||||||
|
|
||||||
|
|
||||||
|
Transform iterator
|
||||||
|
------------------
|
||||||
|
|
||||||
|
.. include:: transform_iterator_abstract.rst
|
||||||
|
|
||||||
|
Class template ``transform_iterator``
|
||||||
|
.....................................
|
||||||
|
|
||||||
|
.. include:: transform_iterator_ref.rst
|
||||||
|
|
||||||
|
|
||||||
|
Filter iterator
|
||||||
|
---------------
|
||||||
|
|
||||||
|
.. include:: filter_iterator_abstract.rst
|
||||||
|
|
||||||
|
|
||||||
|
Class template ``filter_iterator``
|
||||||
|
..................................
|
||||||
|
|
||||||
|
.. include:: filter_iterator_ref.rst
|
||||||
|
|
||||||
|
|
||||||
|
Counting iterator
|
||||||
|
-----------------
|
||||||
|
|
||||||
|
.. include:: counting_iterator_abstract.rst
|
||||||
|
|
||||||
|
Class template ``counting_iterator``
|
||||||
|
....................................
|
||||||
|
|
||||||
|
.. include:: counting_iterator_ref.rst
|
||||||
|
|
||||||
|
|
||||||
|
Function output iterator
|
||||||
|
------------------------
|
||||||
|
|
||||||
|
.. include:: func_output_iter_abstract.rst
|
||||||
|
|
||||||
|
Class template ``function_output_iterator``
|
||||||
|
...........................................
|
||||||
|
|
||||||
|
.. include:: func_output_iter_ref.rst
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
.. LocalWords: Abrahams Siek Witt istream ostream iter MTL strided interoperate
|
||||||
|
LocalWords: CRTP metafunctions inlining lvalue JGS incrementable BGL LEDA cv
|
||||||
|
LocalWords: GraphBase struct ptrdiff UnaryFunction const int typename bool pp
|
||||||
|
LocalWords: lhs rhs SFINAE markup iff tmp OtherDerived OtherIterator DWA foo
|
||||||
|
LocalWords: dereferenceable subobject AdaptableUnaryFunction impl pre ifdef'd
|
||||||
|
LocalWords: OtherIncrementable Coplien
|
53
doc/facade_iterator_category.rst
Normal file
53
doc/facade_iterator_category.rst
Normal file
@ -0,0 +1,53 @@
|
|||||||
|
.. |iterator-category| replace:: *iterator-category*
|
||||||
|
.. _iterator-category:
|
||||||
|
|
||||||
|
.. parsed-literal::
|
||||||
|
|
||||||
|
*iterator-category*\ (C,R,V) :=
|
||||||
|
if (C is convertible to std::input_iterator_tag
|
||||||
|
|| C is convertible to std::output_iterator_tag
|
||||||
|
)
|
||||||
|
return C
|
||||||
|
|
||||||
|
else if (C is not convertible to incrementable_traversal_tag)
|
||||||
|
*the program is ill-formed*
|
||||||
|
|
||||||
|
else return a type X satisfying the following two constraints:
|
||||||
|
|
||||||
|
1. X is convertible to X1, and not to any more-derived
|
||||||
|
type, where X1 is defined by:
|
||||||
|
|
||||||
|
if (R is a reference type
|
||||||
|
&& C is convertible to forward_traversal_tag)
|
||||||
|
{
|
||||||
|
if (C is convertible to random_access_traversal_tag)
|
||||||
|
X1 = random_access_iterator_tag
|
||||||
|
else if (C is convertible to bidirectional_traversal_tag)
|
||||||
|
X1 = bidirectional_iterator_tag
|
||||||
|
else
|
||||||
|
X1 = forward_iterator_tag
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (C is convertible to single_pass_traversal_tag
|
||||||
|
&& R is convertible to V)
|
||||||
|
X1 = input_iterator_tag
|
||||||
|
else
|
||||||
|
X1 = C
|
||||||
|
}
|
||||||
|
|
||||||
|
2. |category-to-traversal|_\ (X) is convertible to the most
|
||||||
|
derived traversal tag type to which X is also
|
||||||
|
convertible, and not to any more-derived traversal tag
|
||||||
|
type.
|
||||||
|
|
||||||
|
.. |category-to-traversal| replace:: *category-to-traversal*
|
||||||
|
.. _`category-to-traversal`: new-iter-concepts.html#category-to-traversal
|
||||||
|
|
||||||
|
[Note: the intention is to allow ``iterator_category`` to be one of
|
||||||
|
the five original category tags when convertibility to one of the
|
||||||
|
traversal tags would add no information]
|
||||||
|
|
||||||
|
.. Copyright David Abrahams 2004. Use, modification and distribution is
|
||||||
|
.. subject to the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
413
doc/filter_iterator.html
Normal file
413
doc/filter_iterator.html
Normal file
@ -0,0 +1,413 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" />
|
||||||
|
<title>Filter Iterator</title>
|
||||||
|
<meta name="author" content="David Abrahams, Jeremy Siek, Thomas Witt" />
|
||||||
|
<meta name="organization" content="Boost Consulting, Indiana University Open Systems Lab, University of Hanover Institute for Transport Railway Operation and Construction" />
|
||||||
|
<meta name="date" content="2006-09-11" />
|
||||||
|
<meta name="copyright" content="Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003." />
|
||||||
|
<link rel="stylesheet" href="../../../rst.css" type="text/css" />
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="filter-iterator">
|
||||||
|
<h1 class="title">Filter Iterator</h1>
|
||||||
|
<table class="docinfo" frame="void" rules="none">
|
||||||
|
<col class="docinfo-name" />
|
||||||
|
<col class="docinfo-content" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><th class="docinfo-name">Author:</th>
|
||||||
|
<td>David Abrahams, Jeremy Siek, Thomas Witt</td></tr>
|
||||||
|
<tr><th class="docinfo-name">Contact:</th>
|
||||||
|
<td><a class="first reference external" href="mailto:dave@boost-consulting.com">dave@boost-consulting.com</a>, <a class="reference external" href="mailto:jsiek@osl.iu.edu">jsiek@osl.iu.edu</a>, <a class="last reference external" href="mailto:witt@ive.uni-hannover.de">witt@ive.uni-hannover.de</a></td></tr>
|
||||||
|
<tr><th class="docinfo-name">Organization:</th>
|
||||||
|
<td><a class="first reference external" href="http://www.boost-consulting.com">Boost Consulting</a>, Indiana University <a class="reference external" href="http://www.osl.iu.edu">Open Systems
|
||||||
|
Lab</a>, University of Hanover <a class="last reference external" href="http://www.ive.uni-hannover.de">Institute for Transport
|
||||||
|
Railway Operation and Construction</a></td></tr>
|
||||||
|
<tr><th class="docinfo-name">Date:</th>
|
||||||
|
<td>2006-09-11</td></tr>
|
||||||
|
<tr><th class="docinfo-name">Copyright:</th>
|
||||||
|
<td>Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003.</td></tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<!-- Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">abstract:</th><td class="field-body"><!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
The filter iterator adaptor creates a view of an iterator range in
|
||||||
|
which some elements of the range are skipped. A predicate function
|
||||||
|
object controls which elements are skipped. When the predicate is
|
||||||
|
applied to an element, if it returns <tt class="docutils literal"><span class="pre">true</span></tt> then the element is
|
||||||
|
retained and if it returns <tt class="docutils literal"><span class="pre">false</span></tt> then the element is skipped
|
||||||
|
over. When skipping over elements, it is necessary for the filter
|
||||||
|
adaptor to know when to stop so as to avoid going past the end of the
|
||||||
|
underlying range. A filter iterator is therefore constructed with pair
|
||||||
|
of iterators indicating the range of elements in the unfiltered
|
||||||
|
sequence to be traversed.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<div class="contents topic" id="table-of-contents">
|
||||||
|
<p class="topic-title first">Table of Contents</p>
|
||||||
|
<ul class="simple">
|
||||||
|
<li><a class="reference internal" href="#filter-iterator-synopsis" id="id2"><tt class="docutils literal"><span class="pre">filter_iterator</span></tt> synopsis</a></li>
|
||||||
|
<li><a class="reference internal" href="#filter-iterator-requirements" id="id3"><tt class="docutils literal"><span class="pre">filter_iterator</span></tt> requirements</a></li>
|
||||||
|
<li><a class="reference internal" href="#filter-iterator-models" id="id4"><tt class="docutils literal"><span class="pre">filter_iterator</span></tt> models</a></li>
|
||||||
|
<li><a class="reference internal" href="#filter-iterator-operations" id="id5"><tt class="docutils literal"><span class="pre">filter_iterator</span></tt> operations</a></li>
|
||||||
|
<li><a class="reference internal" href="#example" id="id6">Example</a></li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="filter-iterator-synopsis">
|
||||||
|
<h1><a class="toc-backref" href="#id2"><tt class="docutils literal"><span class="pre">filter_iterator</span></tt> synopsis</a></h1>
|
||||||
|
<!-- Copyright David Abrahams, Jeremy Siek, and Thomas Witt -->
|
||||||
|
<!-- 2004. Use, modification and distribution is subject to the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying file -->
|
||||||
|
<!-- LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<pre class="literal-block">
|
||||||
|
template <class Predicate, class Iterator>
|
||||||
|
class filter_iterator
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
typedef iterator_traits<Iterator>::value_type value_type;
|
||||||
|
typedef iterator_traits<Iterator>::reference reference;
|
||||||
|
typedef iterator_traits<Iterator>::pointer pointer;
|
||||||
|
typedef iterator_traits<Iterator>::difference_type difference_type;
|
||||||
|
typedef /* see below */ iterator_category;
|
||||||
|
|
||||||
|
filter_iterator();
|
||||||
|
filter_iterator(Predicate f, Iterator x, Iterator end = Iterator());
|
||||||
|
filter_iterator(Iterator x, Iterator end = Iterator());
|
||||||
|
template<class OtherIterator>
|
||||||
|
filter_iterator(
|
||||||
|
filter_iterator<Predicate, OtherIterator> const& t
|
||||||
|
, typename enable_if_convertible<OtherIterator, Iterator>::type* = 0 // exposition
|
||||||
|
);
|
||||||
|
Predicate predicate() const;
|
||||||
|
Iterator end() const;
|
||||||
|
Iterator const& base() const;
|
||||||
|
reference operator*() const;
|
||||||
|
filter_iterator& operator++();
|
||||||
|
private:
|
||||||
|
Predicate m_pred; // exposition only
|
||||||
|
Iterator m_iter; // exposition only
|
||||||
|
Iterator m_end; // exposition only
|
||||||
|
};
|
||||||
|
</pre>
|
||||||
|
<p>If <tt class="docutils literal"><span class="pre">Iterator</span></tt> models Readable Lvalue Iterator and Bidirectional Traversal
|
||||||
|
Iterator then <tt class="docutils literal"><span class="pre">iterator_category</span></tt> is convertible to
|
||||||
|
<tt class="docutils literal"><span class="pre">std::bidirectional_iterator_tag</span></tt>.
|
||||||
|
Otherwise, if <tt class="docutils literal"><span class="pre">Iterator</span></tt> models Readable Lvalue Iterator and Forward Traversal
|
||||||
|
Iterator then <tt class="docutils literal"><span class="pre">iterator_category</span></tt> is convertible to
|
||||||
|
<tt class="docutils literal"><span class="pre">std::forward_iterator_tag</span></tt>.
|
||||||
|
Otherwise <tt class="docutils literal"><span class="pre">iterator_category</span></tt> is
|
||||||
|
convertible to <tt class="docutils literal"><span class="pre">std::input_iterator_tag</span></tt>.</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="filter-iterator-requirements">
|
||||||
|
<h1><a class="toc-backref" href="#id3"><tt class="docutils literal"><span class="pre">filter_iterator</span></tt> requirements</a></h1>
|
||||||
|
<p>The <tt class="docutils literal"><span class="pre">Iterator</span></tt> argument shall meet the requirements of Readable
|
||||||
|
Iterator and Single Pass Iterator or it shall meet the requirements of
|
||||||
|
Input Iterator.</p>
|
||||||
|
<p>The <tt class="docutils literal"><span class="pre">Predicate</span></tt> argument must be Assignable, Copy Constructible, and
|
||||||
|
the expression <tt class="docutils literal"><span class="pre">p(x)</span></tt> must be valid where <tt class="docutils literal"><span class="pre">p</span></tt> is an object of type
|
||||||
|
<tt class="docutils literal"><span class="pre">Predicate</span></tt>, <tt class="docutils literal"><span class="pre">x</span></tt> is an object of type
|
||||||
|
<tt class="docutils literal"><span class="pre">iterator_traits<Iterator>::value_type</span></tt>, and where the type of
|
||||||
|
<tt class="docutils literal"><span class="pre">p(x)</span></tt> must be convertible to <tt class="docutils literal"><span class="pre">bool</span></tt>.</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="filter-iterator-models">
|
||||||
|
<h1><a class="toc-backref" href="#id4"><tt class="docutils literal"><span class="pre">filter_iterator</span></tt> models</a></h1>
|
||||||
|
<p>The concepts that <tt class="docutils literal"><span class="pre">filter_iterator</span></tt> models are dependent on which
|
||||||
|
concepts the <tt class="docutils literal"><span class="pre">Iterator</span></tt> argument models, as specified in the
|
||||||
|
following tables.</p>
|
||||||
|
<table border="1" class="docutils">
|
||||||
|
<colgroup>
|
||||||
|
<col width="44%" />
|
||||||
|
<col width="56%" />
|
||||||
|
</colgroup>
|
||||||
|
<thead valign="bottom">
|
||||||
|
<tr><th class="head">If <tt class="docutils literal"><span class="pre">Iterator</span></tt> models</th>
|
||||||
|
<th class="head">then <tt class="docutils literal"><span class="pre">filter_iterator</span></tt> models</th>
|
||||||
|
</tr>
|
||||||
|
</thead>
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><td>Single Pass Iterator</td>
|
||||||
|
<td>Single Pass Iterator</td>
|
||||||
|
</tr>
|
||||||
|
<tr><td>Forward Traversal Iterator</td>
|
||||||
|
<td>Forward Traversal Iterator</td>
|
||||||
|
</tr>
|
||||||
|
<tr><td>Bidirectional Traversal Iterator</td>
|
||||||
|
<td>Bidirectional Traversal Iterator</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<table border="1" class="docutils">
|
||||||
|
<colgroup>
|
||||||
|
<col width="41%" />
|
||||||
|
<col width="59%" />
|
||||||
|
</colgroup>
|
||||||
|
<thead valign="bottom">
|
||||||
|
<tr><th class="head">If <tt class="docutils literal"><span class="pre">Iterator</span></tt> models</th>
|
||||||
|
<th class="head">then <tt class="docutils literal"><span class="pre">filter_iterator</span></tt> models</th>
|
||||||
|
</tr>
|
||||||
|
</thead>
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><td>Readable Iterator</td>
|
||||||
|
<td>Readable Iterator</td>
|
||||||
|
</tr>
|
||||||
|
<tr><td>Writable Iterator</td>
|
||||||
|
<td>Writable Iterator</td>
|
||||||
|
</tr>
|
||||||
|
<tr><td>Lvalue Iterator</td>
|
||||||
|
<td>Lvalue Iterator</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<table border="1" class="docutils">
|
||||||
|
<colgroup>
|
||||||
|
<col width="63%" />
|
||||||
|
<col width="38%" />
|
||||||
|
</colgroup>
|
||||||
|
<thead valign="bottom">
|
||||||
|
<tr><th class="head">If <tt class="docutils literal"><span class="pre">Iterator</span></tt> models</th>
|
||||||
|
<th class="head">then <tt class="docutils literal"><span class="pre">filter_iterator</span></tt> models</th>
|
||||||
|
</tr>
|
||||||
|
</thead>
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><td>Readable Iterator, Single Pass Iterator</td>
|
||||||
|
<td>Input Iterator</td>
|
||||||
|
</tr>
|
||||||
|
<tr><td>Readable Lvalue Iterator, Forward Traversal Iterator</td>
|
||||||
|
<td>Forward Iterator</td>
|
||||||
|
</tr>
|
||||||
|
<tr><td>Writable Lvalue Iterator, Forward Traversal Iterator</td>
|
||||||
|
<td>Mutable Forward Iterator</td>
|
||||||
|
</tr>
|
||||||
|
<tr><td>Writable Lvalue Iterator, Bidirectional Iterator</td>
|
||||||
|
<td>Mutable Bidirectional Iterator</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">filter_iterator<P1,</span> <span class="pre">X></span></tt> is interoperable with <tt class="docutils literal"><span class="pre">filter_iterator<P2,</span> <span class="pre">Y></span></tt>
|
||||||
|
if and only if <tt class="docutils literal"><span class="pre">X</span></tt> is interoperable with <tt class="docutils literal"><span class="pre">Y</span></tt>.</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="filter-iterator-operations">
|
||||||
|
<h1><a class="toc-backref" href="#id5"><tt class="docutils literal"><span class="pre">filter_iterator</span></tt> operations</a></h1>
|
||||||
|
<p>In addition to those operations required by the concepts that
|
||||||
|
<tt class="docutils literal"><span class="pre">filter_iterator</span></tt> models, <tt class="docutils literal"><span class="pre">filter_iterator</span></tt> provides the following
|
||||||
|
operations.</p>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">filter_iterator();</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Requires:</th><td class="field-body"><tt class="docutils literal"><span class="pre">Predicate</span></tt> and <tt class="docutils literal"><span class="pre">Iterator</span></tt> must be Default Constructible.</td>
|
||||||
|
</tr>
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body">Constructs a <tt class="docutils literal"><span class="pre">filter_iterator</span></tt> whose``m_pred``, <tt class="docutils literal"><span class="pre">m_iter</span></tt>, and <tt class="docutils literal"><span class="pre">m_end</span></tt>
|
||||||
|
members are a default constructed.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">filter_iterator(Predicate</span> <span class="pre">f,</span> <span class="pre">Iterator</span> <span class="pre">x,</span> <span class="pre">Iterator</span> <span class="pre">end</span> <span class="pre">=</span> <span class="pre">Iterator());</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body">Constructs a <tt class="docutils literal"><span class="pre">filter_iterator</span></tt> where <tt class="docutils literal"><span class="pre">m_iter</span></tt> is either
|
||||||
|
the first position in the range <tt class="docutils literal"><span class="pre">[x,end)</span></tt> such that <tt class="docutils literal"><span class="pre">f(*m_iter)</span> <span class="pre">==</span> <span class="pre">true</span></tt>
|
||||||
|
or else``m_iter == end``. The member <tt class="docutils literal"><span class="pre">m_pred</span></tt> is constructed from
|
||||||
|
<tt class="docutils literal"><span class="pre">f</span></tt> and <tt class="docutils literal"><span class="pre">m_end</span></tt> from <tt class="docutils literal"><span class="pre">end</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">filter_iterator(Iterator</span> <span class="pre">x,</span> <span class="pre">Iterator</span> <span class="pre">end</span> <span class="pre">=</span> <span class="pre">Iterator());</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Requires:</th><td class="field-body"><tt class="docutils literal"><span class="pre">Predicate</span></tt> must be Default Constructible and
|
||||||
|
<tt class="docutils literal"><span class="pre">Predicate</span></tt> is a class type (not a function pointer).</td>
|
||||||
|
</tr>
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body">Constructs a <tt class="docutils literal"><span class="pre">filter_iterator</span></tt> where <tt class="docutils literal"><span class="pre">m_iter</span></tt> is either
|
||||||
|
the first position in the range <tt class="docutils literal"><span class="pre">[x,end)</span></tt> such that <tt class="docutils literal"><span class="pre">m_pred(*m_iter)</span> <span class="pre">==</span> <span class="pre">true</span></tt>
|
||||||
|
or else``m_iter == end``. The member <tt class="docutils literal"><span class="pre">m_pred</span></tt> is default constructed.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<pre class="literal-block">
|
||||||
|
template <class OtherIterator>
|
||||||
|
filter_iterator(
|
||||||
|
filter_iterator<Predicate, OtherIterator> const& t
|
||||||
|
, typename enable_if_convertible<OtherIterator, Iterator>::type* = 0 // exposition
|
||||||
|
);``
|
||||||
|
</pre>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Requires:</th><td class="field-body"><tt class="docutils literal"><span class="pre">OtherIterator</span></tt> is implicitly convertible to <tt class="docutils literal"><span class="pre">Iterator</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body">Constructs a filter iterator whose members are copied from <tt class="docutils literal"><span class="pre">t</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">Predicate</span> <span class="pre">predicate()</span> <span class="pre">const;</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">m_pred</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">Iterator</span> <span class="pre">end()</span> <span class="pre">const;</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">m_end</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">Iterator</span> <span class="pre">const&</span> <span class="pre">base()</span> <span class="pre">const;</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">m_iterator</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">reference</span> <span class="pre">operator*()</span> <span class="pre">const;</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">*m_iter</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">filter_iterator&</span> <span class="pre">operator++();</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body">Increments <tt class="docutils literal"><span class="pre">m_iter</span></tt> and then continues to
|
||||||
|
increment <tt class="docutils literal"><span class="pre">m_iter</span></tt> until either <tt class="docutils literal"><span class="pre">m_iter</span> <span class="pre">==</span> <span class="pre">m_end</span></tt>
|
||||||
|
or <tt class="docutils literal"><span class="pre">m_pred(*m_iter)</span> <span class="pre">==</span> <span class="pre">true</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">*this</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<pre class="literal-block">
|
||||||
|
template <class Predicate, class Iterator>
|
||||||
|
filter_iterator<Predicate,Iterator>
|
||||||
|
make_filter_iterator(Predicate f, Iterator x, Iterator end = Iterator());
|
||||||
|
</pre>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body">filter_iterator<Predicate,Iterator>(f, x, end)</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<pre class="literal-block">
|
||||||
|
template <class Predicate, class Iterator>
|
||||||
|
filter_iterator<Predicate,Iterator>
|
||||||
|
make_filter_iterator(Iterator x, Iterator end = Iterator());
|
||||||
|
</pre>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body">filter_iterator<Predicate,Iterator>(x, end)</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
</div>
|
||||||
|
<div class="section" id="example">
|
||||||
|
<h1><a class="toc-backref" href="#id6">Example</a></h1>
|
||||||
|
<p>This example uses <tt class="docutils literal"><span class="pre">filter_iterator</span></tt> and then
|
||||||
|
<tt class="docutils literal"><span class="pre">make_filter_iterator</span></tt> to output only the positive integers from an
|
||||||
|
array of integers. Then <tt class="docutils literal"><span class="pre">make_filter_iterator</span></tt> is is used to output
|
||||||
|
the integers greater than <tt class="docutils literal"><span class="pre">-2</span></tt>.</p>
|
||||||
|
<pre class="literal-block">
|
||||||
|
struct is_positive_number {
|
||||||
|
bool operator()(int x) { return 0 < x; }
|
||||||
|
};
|
||||||
|
|
||||||
|
int main()
|
||||||
|
{
|
||||||
|
int numbers_[] = { 0, -1, 4, -3, 5, 8, -2 };
|
||||||
|
const int N = sizeof(numbers_)/sizeof(int);
|
||||||
|
|
||||||
|
typedef int* base_iterator;
|
||||||
|
base_iterator numbers(numbers_);
|
||||||
|
|
||||||
|
// Example using filter_iterator
|
||||||
|
typedef boost::filter_iterator<is_positive_number, base_iterator>
|
||||||
|
FilterIter;
|
||||||
|
|
||||||
|
is_positive_number predicate;
|
||||||
|
FilterIter filter_iter_first(predicate, numbers, numbers + N);
|
||||||
|
FilterIter filter_iter_last(predicate, numbers + N, numbers + N);
|
||||||
|
|
||||||
|
std::copy(filter_iter_first, filter_iter_last, std::ostream_iterator<int>(std::cout, " "));
|
||||||
|
std::cout << std::endl;
|
||||||
|
|
||||||
|
// Example using make_filter_iterator()
|
||||||
|
std::copy(boost::make_filter_iterator<is_positive_number>(numbers, numbers + N),
|
||||||
|
boost::make_filter_iterator<is_positive_number>(numbers + N, numbers + N),
|
||||||
|
std::ostream_iterator<int>(std::cout, " "));
|
||||||
|
std::cout << std::endl;
|
||||||
|
|
||||||
|
// Another example using make_filter_iterator()
|
||||||
|
std::copy(
|
||||||
|
boost::make_filter_iterator(
|
||||||
|
std::bind2nd(std::greater<int>(), -2)
|
||||||
|
, numbers, numbers + N)
|
||||||
|
|
||||||
|
, boost::make_filter_iterator(
|
||||||
|
std::bind2nd(std::greater<int>(), -2)
|
||||||
|
, numbers + N, numbers + N)
|
||||||
|
|
||||||
|
, std::ostream_iterator<int>(std::cout, " ")
|
||||||
|
);
|
||||||
|
|
||||||
|
std::cout << std::endl;
|
||||||
|
|
||||||
|
return boost::exit_success;
|
||||||
|
}
|
||||||
|
</pre>
|
||||||
|
<p>The output is:</p>
|
||||||
|
<pre class="literal-block">
|
||||||
|
4 5 8
|
||||||
|
4 5 8
|
||||||
|
0 -1 4 5 8
|
||||||
|
</pre>
|
||||||
|
<p>The source code for this example can be found <a class="reference external" href="../example/filter_iterator_example.cpp">here</a>.</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<hr class="footer" />
|
||||||
|
<a class="reference external" href="filter_iterator.rst">View document source</a>.
|
||||||
|
Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
BIN
doc/filter_iterator.pdf
Normal file
BIN
doc/filter_iterator.pdf
Normal file
Binary file not shown.
33
doc/filter_iterator.rst
Normal file
33
doc/filter_iterator.rst
Normal file
@ -0,0 +1,33 @@
|
|||||||
|
.. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
+++++++++++++++++
|
||||||
|
Filter Iterator
|
||||||
|
+++++++++++++++++
|
||||||
|
|
||||||
|
:Author: David Abrahams, Jeremy Siek, Thomas Witt
|
||||||
|
:Contact: dave@boost-consulting.com, jsiek@osl.iu.edu, witt@ive.uni-hannover.de
|
||||||
|
:organization: `Boost Consulting`_, Indiana University `Open Systems
|
||||||
|
Lab`_, University of Hanover `Institute for Transport
|
||||||
|
Railway Operation and Construction`_
|
||||||
|
:date: $Date$
|
||||||
|
:copyright: Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003.
|
||||||
|
|
||||||
|
.. _`Boost Consulting`: http://www.boost-consulting.com
|
||||||
|
.. _`Open Systems Lab`: http://www.osl.iu.edu
|
||||||
|
.. _`Institute for Transport Railway Operation and Construction`: http://www.ive.uni-hannover.de
|
||||||
|
|
||||||
|
:abstract:
|
||||||
|
|
||||||
|
.. include:: filter_iterator_abstract.rst
|
||||||
|
|
||||||
|
.. contents:: Table of Contents
|
||||||
|
|
||||||
|
``filter_iterator`` synopsis
|
||||||
|
............................
|
||||||
|
|
||||||
|
.. include:: filter_iterator_ref.rst
|
||||||
|
.. include:: make_filter_iterator.rst
|
||||||
|
|
||||||
|
.. include:: filter_iterator_eg.rst
|
15
doc/filter_iterator_abstract.rst
Normal file
15
doc/filter_iterator_abstract.rst
Normal file
@ -0,0 +1,15 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
The filter iterator adaptor creates a view of an iterator range in
|
||||||
|
which some elements of the range are skipped. A predicate function
|
||||||
|
object controls which elements are skipped. When the predicate is
|
||||||
|
applied to an element, if it returns ``true`` then the element is
|
||||||
|
retained and if it returns ``false`` then the element is skipped
|
||||||
|
over. When skipping over elements, it is necessary for the filter
|
||||||
|
adaptor to know when to stop so as to avoid going past the end of the
|
||||||
|
underlying range. A filter iterator is therefore constructed with pair
|
||||||
|
of iterators indicating the range of elements in the unfiltered
|
||||||
|
sequence to be traversed.
|
||||||
|
|
72
doc/filter_iterator_eg.rst
Normal file
72
doc/filter_iterator_eg.rst
Normal file
@ -0,0 +1,72 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
Example
|
||||||
|
.......
|
||||||
|
|
||||||
|
This example uses ``filter_iterator`` and then
|
||||||
|
``make_filter_iterator`` to output only the positive integers from an
|
||||||
|
array of integers. Then ``make_filter_iterator`` is is used to output
|
||||||
|
the integers greater than ``-2``.
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
struct is_positive_number {
|
||||||
|
bool operator()(int x) { return 0 < x; }
|
||||||
|
};
|
||||||
|
|
||||||
|
int main()
|
||||||
|
{
|
||||||
|
int numbers_[] = { 0, -1, 4, -3, 5, 8, -2 };
|
||||||
|
const int N = sizeof(numbers_)/sizeof(int);
|
||||||
|
|
||||||
|
typedef int* base_iterator;
|
||||||
|
base_iterator numbers(numbers_);
|
||||||
|
|
||||||
|
// Example using filter_iterator
|
||||||
|
typedef boost::filter_iterator<is_positive_number, base_iterator>
|
||||||
|
FilterIter;
|
||||||
|
|
||||||
|
is_positive_number predicate;
|
||||||
|
FilterIter filter_iter_first(predicate, numbers, numbers + N);
|
||||||
|
FilterIter filter_iter_last(predicate, numbers + N, numbers + N);
|
||||||
|
|
||||||
|
std::copy(filter_iter_first, filter_iter_last, std::ostream_iterator<int>(std::cout, " "));
|
||||||
|
std::cout << std::endl;
|
||||||
|
|
||||||
|
// Example using make_filter_iterator()
|
||||||
|
std::copy(boost::make_filter_iterator<is_positive_number>(numbers, numbers + N),
|
||||||
|
boost::make_filter_iterator<is_positive_number>(numbers + N, numbers + N),
|
||||||
|
std::ostream_iterator<int>(std::cout, " "));
|
||||||
|
std::cout << std::endl;
|
||||||
|
|
||||||
|
// Another example using make_filter_iterator()
|
||||||
|
std::copy(
|
||||||
|
boost::make_filter_iterator(
|
||||||
|
std::bind2nd(std::greater<int>(), -2)
|
||||||
|
, numbers, numbers + N)
|
||||||
|
|
||||||
|
, boost::make_filter_iterator(
|
||||||
|
std::bind2nd(std::greater<int>(), -2)
|
||||||
|
, numbers + N, numbers + N)
|
||||||
|
|
||||||
|
, std::ostream_iterator<int>(std::cout, " ")
|
||||||
|
);
|
||||||
|
|
||||||
|
std::cout << std::endl;
|
||||||
|
|
||||||
|
return boost::exit_success;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
The output is::
|
||||||
|
|
||||||
|
4 5 8
|
||||||
|
4 5 8
|
||||||
|
0 -1 4 5 8
|
||||||
|
|
||||||
|
|
||||||
|
The source code for this example can be found `here`__.
|
||||||
|
|
||||||
|
__ ../example/filter_iterator_example.cpp
|
177
doc/filter_iterator_ref.rst
Normal file
177
doc/filter_iterator_ref.rst
Normal file
@ -0,0 +1,177 @@
|
|||||||
|
.. Copyright David Abrahams, Jeremy Siek, and Thomas Witt
|
||||||
|
.. 2004. Use, modification and distribution is subject to the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying file
|
||||||
|
.. LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <class Predicate, class Iterator>
|
||||||
|
class filter_iterator
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
typedef iterator_traits<Iterator>::value_type value_type;
|
||||||
|
typedef iterator_traits<Iterator>::reference reference;
|
||||||
|
typedef iterator_traits<Iterator>::pointer pointer;
|
||||||
|
typedef iterator_traits<Iterator>::difference_type difference_type;
|
||||||
|
typedef /* see below */ iterator_category;
|
||||||
|
|
||||||
|
filter_iterator();
|
||||||
|
filter_iterator(Predicate f, Iterator x, Iterator end = Iterator());
|
||||||
|
filter_iterator(Iterator x, Iterator end = Iterator());
|
||||||
|
template<class OtherIterator>
|
||||||
|
filter_iterator(
|
||||||
|
filter_iterator<Predicate, OtherIterator> const& t
|
||||||
|
, typename enable_if_convertible<OtherIterator, Iterator>::type* = 0 // exposition
|
||||||
|
);
|
||||||
|
Predicate predicate() const;
|
||||||
|
Iterator end() const;
|
||||||
|
Iterator const& base() const;
|
||||||
|
reference operator*() const;
|
||||||
|
filter_iterator& operator++();
|
||||||
|
private:
|
||||||
|
Predicate m_pred; // exposition only
|
||||||
|
Iterator m_iter; // exposition only
|
||||||
|
Iterator m_end; // exposition only
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
If ``Iterator`` models Readable Lvalue Iterator and Bidirectional Traversal
|
||||||
|
Iterator then ``iterator_category`` is convertible to
|
||||||
|
``std::bidirectional_iterator_tag``.
|
||||||
|
Otherwise, if ``Iterator`` models Readable Lvalue Iterator and Forward Traversal
|
||||||
|
Iterator then ``iterator_category`` is convertible to
|
||||||
|
``std::forward_iterator_tag``.
|
||||||
|
Otherwise ``iterator_category`` is
|
||||||
|
convertible to ``std::input_iterator_tag``.
|
||||||
|
|
||||||
|
|
||||||
|
``filter_iterator`` requirements
|
||||||
|
................................
|
||||||
|
|
||||||
|
The ``Iterator`` argument shall meet the requirements of Readable
|
||||||
|
Iterator and Single Pass Iterator or it shall meet the requirements of
|
||||||
|
Input Iterator.
|
||||||
|
|
||||||
|
The ``Predicate`` argument must be Assignable, Copy Constructible, and
|
||||||
|
the expression ``p(x)`` must be valid where ``p`` is an object of type
|
||||||
|
``Predicate``, ``x`` is an object of type
|
||||||
|
``iterator_traits<Iterator>::value_type``, and where the type of
|
||||||
|
``p(x)`` must be convertible to ``bool``.
|
||||||
|
|
||||||
|
|
||||||
|
``filter_iterator`` models
|
||||||
|
..........................
|
||||||
|
|
||||||
|
The concepts that ``filter_iterator`` models are dependent on which
|
||||||
|
concepts the ``Iterator`` argument models, as specified in the
|
||||||
|
following tables.
|
||||||
|
|
||||||
|
+---------------------------------+------------------------------------------+
|
||||||
|
|If ``Iterator`` models |then ``filter_iterator`` models |
|
||||||
|
+=================================+==========================================+
|
||||||
|
|Single Pass Iterator |Single Pass Iterator |
|
||||||
|
+---------------------------------+------------------------------------------+
|
||||||
|
|Forward Traversal Iterator |Forward Traversal Iterator |
|
||||||
|
+---------------------------------+------------------------------------------+
|
||||||
|
|Bidirectional Traversal Iterator |Bidirectional Traversal Iterator |
|
||||||
|
+---------------------------------+------------------------------------------+
|
||||||
|
|
||||||
|
+--------------------------------+----------------------------------------------+
|
||||||
|
| If ``Iterator`` models | then ``filter_iterator`` models |
|
||||||
|
+================================+==============================================+
|
||||||
|
| Readable Iterator | Readable Iterator |
|
||||||
|
+--------------------------------+----------------------------------------------+
|
||||||
|
| Writable Iterator | Writable Iterator |
|
||||||
|
+--------------------------------+----------------------------------------------+
|
||||||
|
| Lvalue Iterator | Lvalue Iterator |
|
||||||
|
+--------------------------------+----------------------------------------------+
|
||||||
|
|
||||||
|
+-------------------------------------------------------+---------------------------------+
|
||||||
|
|If ``Iterator`` models | then ``filter_iterator`` models |
|
||||||
|
+=======================================================+=================================+
|
||||||
|
|Readable Iterator, Single Pass Iterator | Input Iterator |
|
||||||
|
+-------------------------------------------------------+---------------------------------+
|
||||||
|
|Readable Lvalue Iterator, Forward Traversal Iterator | Forward Iterator |
|
||||||
|
+-------------------------------------------------------+---------------------------------+
|
||||||
|
|Writable Lvalue Iterator, Forward Traversal Iterator | Mutable Forward Iterator |
|
||||||
|
+-------------------------------------------------------+---------------------------------+
|
||||||
|
|Writable Lvalue Iterator, Bidirectional Iterator | Mutable Bidirectional Iterator |
|
||||||
|
+-------------------------------------------------------+---------------------------------+
|
||||||
|
|
||||||
|
|
||||||
|
``filter_iterator<P1, X>`` is interoperable with ``filter_iterator<P2, Y>``
|
||||||
|
if and only if ``X`` is interoperable with ``Y``.
|
||||||
|
|
||||||
|
|
||||||
|
``filter_iterator`` operations
|
||||||
|
..............................
|
||||||
|
|
||||||
|
In addition to those operations required by the concepts that
|
||||||
|
``filter_iterator`` models, ``filter_iterator`` provides the following
|
||||||
|
operations.
|
||||||
|
|
||||||
|
|
||||||
|
``filter_iterator();``
|
||||||
|
|
||||||
|
:Requires: ``Predicate`` and ``Iterator`` must be Default Constructible.
|
||||||
|
:Effects: Constructs a ``filter_iterator`` whose``m_pred``, ``m_iter``, and ``m_end``
|
||||||
|
members are a default constructed.
|
||||||
|
|
||||||
|
|
||||||
|
``filter_iterator(Predicate f, Iterator x, Iterator end = Iterator());``
|
||||||
|
|
||||||
|
:Effects: Constructs a ``filter_iterator`` where ``m_iter`` is either
|
||||||
|
the first position in the range ``[x,end)`` such that ``f(*m_iter) == true``
|
||||||
|
or else``m_iter == end``. The member ``m_pred`` is constructed from
|
||||||
|
``f`` and ``m_end`` from ``end``.
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
``filter_iterator(Iterator x, Iterator end = Iterator());``
|
||||||
|
|
||||||
|
:Requires: ``Predicate`` must be Default Constructible and
|
||||||
|
``Predicate`` is a class type (not a function pointer).
|
||||||
|
:Effects: Constructs a ``filter_iterator`` where ``m_iter`` is either
|
||||||
|
the first position in the range ``[x,end)`` such that ``m_pred(*m_iter) == true``
|
||||||
|
or else``m_iter == end``. The member ``m_pred`` is default constructed.
|
||||||
|
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <class OtherIterator>
|
||||||
|
filter_iterator(
|
||||||
|
filter_iterator<Predicate, OtherIterator> const& t
|
||||||
|
, typename enable_if_convertible<OtherIterator, Iterator>::type* = 0 // exposition
|
||||||
|
);``
|
||||||
|
|
||||||
|
:Requires: ``OtherIterator`` is implicitly convertible to ``Iterator``.
|
||||||
|
:Effects: Constructs a filter iterator whose members are copied from ``t``.
|
||||||
|
|
||||||
|
|
||||||
|
``Predicate predicate() const;``
|
||||||
|
|
||||||
|
:Returns: ``m_pred``
|
||||||
|
|
||||||
|
|
||||||
|
``Iterator end() const;``
|
||||||
|
|
||||||
|
:Returns: ``m_end``
|
||||||
|
|
||||||
|
|
||||||
|
``Iterator const& base() const;``
|
||||||
|
|
||||||
|
:Returns: ``m_iterator``
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
``reference operator*() const;``
|
||||||
|
|
||||||
|
:Returns: ``*m_iter``
|
||||||
|
|
||||||
|
|
||||||
|
``filter_iterator& operator++();``
|
||||||
|
|
||||||
|
:Effects: Increments ``m_iter`` and then continues to
|
||||||
|
increment ``m_iter`` until either ``m_iter == m_end``
|
||||||
|
or ``m_pred(*m_iter) == true``.
|
||||||
|
:Returns: ``*this``
|
12
doc/func_output_iter_abstract.rst
Normal file
12
doc/func_output_iter_abstract.rst
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
The function output iterator adaptor makes it easier to create custom
|
||||||
|
output iterators. The adaptor takes a unary function and creates a
|
||||||
|
model of Output Iterator. Each item assigned to the output iterator is
|
||||||
|
passed as an argument to the unary function. The motivation for this
|
||||||
|
iterator is that creating a conforming output iterator is non-trivial,
|
||||||
|
particularly because the proper implementation usually requires a
|
||||||
|
proxy object.
|
||||||
|
|
73
doc/func_output_iter_ref.rst
Normal file
73
doc/func_output_iter_ref.rst
Normal file
@ -0,0 +1,73 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
Header
|
||||||
|
......
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
#include <boost/function_output_iterator.hpp>
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <class UnaryFunction>
|
||||||
|
class function_output_iterator {
|
||||||
|
public:
|
||||||
|
typedef std::output_iterator_tag iterator_category;
|
||||||
|
typedef void value_type;
|
||||||
|
typedef void difference_type;
|
||||||
|
typedef void pointer;
|
||||||
|
typedef void reference;
|
||||||
|
|
||||||
|
explicit function_output_iterator();
|
||||||
|
|
||||||
|
explicit function_output_iterator(const UnaryFunction& f);
|
||||||
|
|
||||||
|
/* see below */ operator*();
|
||||||
|
function_output_iterator& operator++();
|
||||||
|
function_output_iterator& operator++(int);
|
||||||
|
private:
|
||||||
|
UnaryFunction m_f; // exposition only
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
``function_output_iterator`` requirements
|
||||||
|
.........................................
|
||||||
|
|
||||||
|
``UnaryFunction`` must be Assignable and Copy Constructible.
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
``function_output_iterator`` models
|
||||||
|
...................................
|
||||||
|
|
||||||
|
``function_output_iterator`` is a model of the Writable and
|
||||||
|
Incrementable Iterator concepts.
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
``function_output_iterator`` operations
|
||||||
|
.......................................
|
||||||
|
|
||||||
|
``explicit function_output_iterator(const UnaryFunction& f = UnaryFunction());``
|
||||||
|
|
||||||
|
:Effects: Constructs an instance of ``function_output_iterator``
|
||||||
|
with ``m_f`` constructed from ``f``.
|
||||||
|
|
||||||
|
|
||||||
|
``operator*();``
|
||||||
|
|
||||||
|
:Returns: An object ``r`` of unspecified type such that ``r = t``
|
||||||
|
is equivalent to ``m_f(t)`` for all ``t``.
|
||||||
|
|
||||||
|
|
||||||
|
``function_output_iterator& operator++();``
|
||||||
|
|
||||||
|
:Returns: ``*this``
|
||||||
|
|
||||||
|
|
||||||
|
``function_output_iterator& operator++(int);``
|
||||||
|
|
||||||
|
:Returns: ``*this``
|
191
doc/function_output_iterator.html
Normal file
191
doc/function_output_iterator.html
Normal file
@ -0,0 +1,191 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" />
|
||||||
|
<title>Function Output Iterator</title>
|
||||||
|
<meta name="author" content="David Abrahams, Jeremy Siek, Thomas Witt" />
|
||||||
|
<meta name="organization" content="Boost Consulting, Indiana University Open Systems Lab, University of Hanover Institute for Transport Railway Operation and Construction" />
|
||||||
|
<meta name="date" content="2006-09-11" />
|
||||||
|
<meta name="copyright" content="Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003." />
|
||||||
|
<link rel="stylesheet" href="../../../rst.css" type="text/css" />
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="function-output-iterator">
|
||||||
|
<h1 class="title">Function Output Iterator</h1>
|
||||||
|
<table class="docinfo" frame="void" rules="none">
|
||||||
|
<col class="docinfo-name" />
|
||||||
|
<col class="docinfo-content" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><th class="docinfo-name">Author:</th>
|
||||||
|
<td>David Abrahams, Jeremy Siek, Thomas Witt</td></tr>
|
||||||
|
<tr><th class="docinfo-name">Contact:</th>
|
||||||
|
<td><a class="first reference external" href="mailto:dave@boost-consulting.com">dave@boost-consulting.com</a>, <a class="reference external" href="mailto:jsiek@osl.iu.edu">jsiek@osl.iu.edu</a>, <a class="last reference external" href="mailto:witt@ive.uni-hannover.de">witt@ive.uni-hannover.de</a></td></tr>
|
||||||
|
<tr><th class="docinfo-name">Organization:</th>
|
||||||
|
<td><a class="first reference external" href="http://www.boost-consulting.com">Boost Consulting</a>, Indiana University <a class="reference external" href="http://www.osl.iu.edu">Open Systems
|
||||||
|
Lab</a>, University of Hanover <a class="last reference external" href="http://www.ive.uni-hannover.de">Institute for Transport
|
||||||
|
Railway Operation and Construction</a></td></tr>
|
||||||
|
<tr><th class="docinfo-name">Date:</th>
|
||||||
|
<td>2006-09-11</td></tr>
|
||||||
|
<tr><th class="docinfo-name">Copyright:</th>
|
||||||
|
<td>Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003.</td></tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<!-- Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">abstract:</th><td class="field-body"><!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
The function output iterator adaptor makes it easier to create custom
|
||||||
|
output iterators. The adaptor takes a unary function and creates a
|
||||||
|
model of Output Iterator. Each item assigned to the output iterator is
|
||||||
|
passed as an argument to the unary function. The motivation for this
|
||||||
|
iterator is that creating a conforming output iterator is non-trivial,
|
||||||
|
particularly because the proper implementation usually requires a
|
||||||
|
proxy object.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<div class="contents topic" id="table-of-contents">
|
||||||
|
<p class="topic-title first">Table of Contents</p>
|
||||||
|
<ul class="simple">
|
||||||
|
<li><a class="reference internal" href="#header" id="id1">Header</a></li>
|
||||||
|
<li><a class="reference internal" href="#function-output-iterator-requirements" id="id2"><tt class="docutils literal"><span class="pre">function_output_iterator</span></tt> requirements</a></li>
|
||||||
|
<li><a class="reference internal" href="#function-output-iterator-models" id="id3"><tt class="docutils literal"><span class="pre">function_output_iterator</span></tt> models</a></li>
|
||||||
|
<li><a class="reference internal" href="#function-output-iterator-operations" id="id4"><tt class="docutils literal"><span class="pre">function_output_iterator</span></tt> operations</a></li>
|
||||||
|
<li><a class="reference internal" href="#example" id="id5">Example</a></li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<div class="section" id="header">
|
||||||
|
<h1><a class="toc-backref" href="#id1">Header</a></h1>
|
||||||
|
<pre class="literal-block">
|
||||||
|
#include <boost/function_output_iterator.hpp>
|
||||||
|
</pre>
|
||||||
|
<pre class="literal-block">
|
||||||
|
template <class UnaryFunction>
|
||||||
|
class function_output_iterator {
|
||||||
|
public:
|
||||||
|
typedef std::output_iterator_tag iterator_category;
|
||||||
|
typedef void value_type;
|
||||||
|
typedef void difference_type;
|
||||||
|
typedef void pointer;
|
||||||
|
typedef void reference;
|
||||||
|
|
||||||
|
explicit function_output_iterator();
|
||||||
|
|
||||||
|
explicit function_output_iterator(const UnaryFunction& f);
|
||||||
|
|
||||||
|
/* see below */ operator*();
|
||||||
|
function_output_iterator& operator++();
|
||||||
|
function_output_iterator& operator++(int);
|
||||||
|
private:
|
||||||
|
UnaryFunction m_f; // exposition only
|
||||||
|
};
|
||||||
|
</pre>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="function-output-iterator-requirements">
|
||||||
|
<h1><a class="toc-backref" href="#id2"><tt class="docutils literal"><span class="pre">function_output_iterator</span></tt> requirements</a></h1>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">UnaryFunction</span></tt> must be Assignable and Copy Constructible.</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="function-output-iterator-models">
|
||||||
|
<h1><a class="toc-backref" href="#id3"><tt class="docutils literal"><span class="pre">function_output_iterator</span></tt> models</a></h1>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">function_output_iterator</span></tt> is a model of the Writable and
|
||||||
|
Incrementable Iterator concepts.</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="function-output-iterator-operations">
|
||||||
|
<h1><a class="toc-backref" href="#id4"><tt class="docutils literal"><span class="pre">function_output_iterator</span></tt> operations</a></h1>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">explicit</span> <span class="pre">function_output_iterator(const</span> <span class="pre">UnaryFunction&</span> <span class="pre">f</span> <span class="pre">=</span> <span class="pre">UnaryFunction());</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body">Constructs an instance of <tt class="docutils literal"><span class="pre">function_output_iterator</span></tt>
|
||||||
|
with <tt class="docutils literal"><span class="pre">m_f</span></tt> constructed from <tt class="docutils literal"><span class="pre">f</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">operator*();</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body">An object <tt class="docutils literal"><span class="pre">r</span></tt> of unspecified type such that <tt class="docutils literal"><span class="pre">r</span> <span class="pre">=</span> <span class="pre">t</span></tt>
|
||||||
|
is equivalent to <tt class="docutils literal"><span class="pre">m_f(t)</span></tt> for all <tt class="docutils literal"><span class="pre">t</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">function_output_iterator&</span> <span class="pre">operator++();</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">*this</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">function_output_iterator&</span> <span class="pre">operator++(int);</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">*this</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
</div>
|
||||||
|
<div class="section" id="example">
|
||||||
|
<h1><a class="toc-backref" href="#id5">Example</a></h1>
|
||||||
|
<pre class="literal-block">
|
||||||
|
struct string_appender
|
||||||
|
{
|
||||||
|
string_appender(std::string& s)
|
||||||
|
: m_str(&s)
|
||||||
|
{}
|
||||||
|
|
||||||
|
void operator()(const std::string& x) const
|
||||||
|
{
|
||||||
|
*m_str += x;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::string* m_str;
|
||||||
|
};
|
||||||
|
|
||||||
|
int main(int, char*[])
|
||||||
|
{
|
||||||
|
std::vector<std::string> x;
|
||||||
|
x.push_back("hello");
|
||||||
|
x.push_back(" ");
|
||||||
|
x.push_back("world");
|
||||||
|
x.push_back("!");
|
||||||
|
|
||||||
|
std::string s = "";
|
||||||
|
std::copy(x.begin(), x.end(),
|
||||||
|
boost::make_function_output_iterator(string_appender(s)));
|
||||||
|
|
||||||
|
std::cout << s << std::endl;
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
</pre>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<hr class="footer" />
|
||||||
|
<a class="reference external" href="function_output_iterator.rst">View document source</a>.
|
||||||
|
Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
BIN
doc/function_output_iterator.pdf
Normal file
BIN
doc/function_output_iterator.pdf
Normal file
Binary file not shown.
28
doc/function_output_iterator.rst
Normal file
28
doc/function_output_iterator.rst
Normal file
@ -0,0 +1,28 @@
|
|||||||
|
.. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
++++++++++++++++++++++++++
|
||||||
|
Function Output Iterator
|
||||||
|
++++++++++++++++++++++++++
|
||||||
|
|
||||||
|
:Author: David Abrahams, Jeremy Siek, Thomas Witt
|
||||||
|
:Contact: dave@boost-consulting.com, jsiek@osl.iu.edu, witt@ive.uni-hannover.de
|
||||||
|
:organization: `Boost Consulting`_, Indiana University `Open Systems
|
||||||
|
Lab`_, University of Hanover `Institute for Transport
|
||||||
|
Railway Operation and Construction`_
|
||||||
|
:date: $Date$
|
||||||
|
:copyright: Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003.
|
||||||
|
|
||||||
|
.. _`Boost Consulting`: http://www.boost-consulting.com
|
||||||
|
.. _`Open Systems Lab`: http://www.osl.iu.edu
|
||||||
|
.. _`Institute for Transport Railway Operation and Construction`: http://www.ive.uni-hannover.de
|
||||||
|
|
||||||
|
:abstract:
|
||||||
|
|
||||||
|
.. include:: func_output_iter_abstract.rst
|
||||||
|
|
||||||
|
.. contents:: Table of Contents
|
||||||
|
|
||||||
|
.. include:: func_output_iter_ref.rst
|
||||||
|
.. include:: function_output_iterator_eg.rst
|
39
doc/function_output_iterator_eg.rst
Normal file
39
doc/function_output_iterator_eg.rst
Normal file
@ -0,0 +1,39 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
Example
|
||||||
|
.......
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
struct string_appender
|
||||||
|
{
|
||||||
|
string_appender(std::string& s)
|
||||||
|
: m_str(&s)
|
||||||
|
{}
|
||||||
|
|
||||||
|
void operator()(const std::string& x) const
|
||||||
|
{
|
||||||
|
*m_str += x;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::string* m_str;
|
||||||
|
};
|
||||||
|
|
||||||
|
int main(int, char*[])
|
||||||
|
{
|
||||||
|
std::vector<std::string> x;
|
||||||
|
x.push_back("hello");
|
||||||
|
x.push_back(" ");
|
||||||
|
x.push_back("world");
|
||||||
|
x.push_back("!");
|
||||||
|
|
||||||
|
std::string s = "";
|
||||||
|
std::copy(x.begin(), x.end(),
|
||||||
|
boost::make_function_output_iterator(string_appender(s)));
|
||||||
|
|
||||||
|
std::cout << s << std::endl;
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
32
doc/generate.py
Normal file
32
doc/generate.py
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
#!/usr/bin/python
|
||||||
|
# Copyright David Abrahams 2004. Use, modification and distribution is
|
||||||
|
# subject to the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
# file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
#
|
||||||
|
# Generate html, TeX, and PDF versions of all the source files
|
||||||
|
#
|
||||||
|
import os
|
||||||
|
import sys
|
||||||
|
|
||||||
|
from syscmd import syscmd
|
||||||
|
from sources import sources
|
||||||
|
|
||||||
|
if 0:
|
||||||
|
for s in sources:
|
||||||
|
syscmd('boosthtml %s' % s)
|
||||||
|
else:
|
||||||
|
extensions = ('html', 'pdf')
|
||||||
|
|
||||||
|
if len(sys.argv) > 1:
|
||||||
|
extensions = sys.argv[1:]
|
||||||
|
|
||||||
|
all = [ '%s.%s' % (os.path.splitext(s)[0],ext)
|
||||||
|
for ext in extensions
|
||||||
|
for s in sources
|
||||||
|
]
|
||||||
|
|
||||||
|
print 'make %s' % ' '.join(all)
|
||||||
|
syscmd('make %s' % ' '.join(all))
|
||||||
|
|
||||||
|
|
249
doc/index.html
Normal file
249
doc/index.html
Normal file
@ -0,0 +1,249 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" />
|
||||||
|
<title>The Boost.Iterator Library Boost</title>
|
||||||
|
<link rel="stylesheet" href="../../../rst.css" type="text/css" />
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="the-boost-iterator-library-logo">
|
||||||
|
<h1 class="title">The Boost.Iterator Library <a class="reference external" href="../../../index.htm"><img alt="Boost" src="../../../boost.png" /></a></h1>
|
||||||
|
|
||||||
|
<!-- Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<!-- Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<hr class="docutils" />
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Authors:</th><td class="field-body">David Abrahams, Jeremy Siek, Thomas Witt</td>
|
||||||
|
</tr>
|
||||||
|
<tr class="field"><th class="field-name">Contact:</th><td class="field-body"><a class="reference external" href="mailto:dave@boost-consulting.com">dave@boost-consulting.com</a>, <a class="reference external" href="mailto:jsiek@osl.iu.edu">jsiek@osl.iu.edu</a>, <a class="reference external" href="mailto:witt@styleadvisor.com">witt@styleadvisor.com</a></td>
|
||||||
|
</tr>
|
||||||
|
<tr class="field"><th class="field-name">organizations:</th><td class="field-body"><a class="reference external" href="http://www.boost-consulting.com">Boost Consulting</a>, Indiana University <a class="reference external" href="http://www.osl.iu.edu">Open Systems
|
||||||
|
Lab</a>, <a class="reference external" href="http://www.styleadvisor.com">Zephyr Associates, Inc.</a></td>
|
||||||
|
</tr>
|
||||||
|
<tr class="field"><th class="field-name">date:</th><td class="field-body">$Date$</td>
|
||||||
|
</tr>
|
||||||
|
<tr class="field"><th class="field-name">copyright:</th><td class="field-body">Copyright David Abrahams, Jeremy Siek, Thomas Witt 2003.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Abstract:</th><td class="field-body">The Boost Iterator Library contains two parts. The first
|
||||||
|
is a system of <a class="reference external" href="http://www.boost.org/more/generic_programming.html#concept">concepts</a> which extend the C++ standard
|
||||||
|
iterator requirements. The second is a framework of
|
||||||
|
components for building iterators based on these
|
||||||
|
extended concepts and includes several useful iterator
|
||||||
|
adaptors. The extended iterator concepts have been
|
||||||
|
carefully designed so that old-style iterators
|
||||||
|
can fit in the new concepts and so that new-style
|
||||||
|
iterators will be compatible with old-style algorithms,
|
||||||
|
though algorithms may need to be updated if they want to
|
||||||
|
take full advantage of the new-style iterator
|
||||||
|
capabilities. Several components of this library have
|
||||||
|
been accepted into the C++ standard technical report.
|
||||||
|
The components of the Boost Iterator Library replace the
|
||||||
|
older Boost Iterator Adaptor Library.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<div class="contents topic" id="table-of-contents">
|
||||||
|
<p class="topic-title first"><strong>Table of Contents</strong></p>
|
||||||
|
<ul class="simple">
|
||||||
|
<li><a class="reference internal" href="#new-style-iterators" id="id22">New-Style Iterators</a></li>
|
||||||
|
<li><a class="reference internal" href="#iterator-facade-and-adaptor" id="id23">Iterator Facade and Adaptor</a></li>
|
||||||
|
<li><a class="reference internal" href="#specialized-adaptors" id="id24">Specialized Adaptors</a></li>
|
||||||
|
<li><a class="reference internal" href="#iterator-utilities" id="id25">Iterator Utilities</a><ul>
|
||||||
|
<li><a class="reference internal" href="#traits" id="id26">Traits</a></li>
|
||||||
|
<li><a class="reference internal" href="#testing-and-concept-checking" id="id27">Testing and Concept Checking</a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#upgrading-from-the-old-boost-iterator-adaptor-library" id="id28">Upgrading from the old Boost Iterator Adaptor Library</a></li>
|
||||||
|
<li><a class="reference internal" href="#history" id="id29">History</a></li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
<hr class="docutils" />
|
||||||
|
<div class="section" id="new-style-iterators">
|
||||||
|
<h1><a class="toc-backref" href="#id22">New-Style Iterators</a></h1>
|
||||||
|
<p>The iterator categories defined in C++98 are extremely limiting
|
||||||
|
because they bind together two orthogonal concepts: traversal and
|
||||||
|
element access. For example, because a random access iterator is
|
||||||
|
required to return a reference (and not a proxy) when dereferenced,
|
||||||
|
it is impossible to capture the capabilities of
|
||||||
|
<tt class="docutils literal"><span class="pre">vector<bool>::iterator</span></tt> using the C++98 categories. This is the
|
||||||
|
infamous "<tt class="docutils literal"><span class="pre">vector<bool></span></tt> is not a container, and its iterators
|
||||||
|
aren't random access iterators", debacle about which Herb Sutter
|
||||||
|
wrote two papers for the standards comittee (<a class="reference external" href="http://www.gotw.ca/publications/N1185.pdf">n1185</a> and <a class="reference external" href="http://www.gotw.ca/publications/N1211.pdf">n1211</a>),
|
||||||
|
and a <a class="reference external" href="http://www.gotw.ca/gotw/050.htm">Guru of the Week</a>. New-style iterators go well beyond
|
||||||
|
patching up <tt class="docutils literal"><span class="pre">vector<bool></span></tt>, though: there are lots of other
|
||||||
|
iterators already in use which can't be adequately represented by
|
||||||
|
the existing concepts. For details about the new iterator
|
||||||
|
concepts, see our</p>
|
||||||
|
<blockquote>
|
||||||
|
<a class="reference external" href="new-iter-concepts.html">Standard Proposal For New-Style Iterators</a> (<a class="reference external" href="new-iter-concepts.pdf">PDF</a>)</blockquote>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="iterator-facade-and-adaptor">
|
||||||
|
<h1><a class="toc-backref" href="#id23">Iterator Facade and Adaptor</a></h1>
|
||||||
|
<p>Writing standard-conforming iterators is tricky, but the need comes
|
||||||
|
up often. In order to ease the implementation of new iterators,
|
||||||
|
the Boost.Iterator library provides the <tt class="docutils literal"><span class="pre">iterator_facade</span></tt> class template,
|
||||||
|
which implements many useful defaults and compile-time checks
|
||||||
|
designed to help the iterator author ensure that his iterator is
|
||||||
|
correct.</p>
|
||||||
|
<p>It is also common to define a new iterator that is similar to some
|
||||||
|
underlying iterator or iterator-like type, but that modifies some
|
||||||
|
aspect of the underlying type's behavior. For that purpose, the
|
||||||
|
library supplies the <tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> class template, which is specially
|
||||||
|
designed to take advantage of as much of the underlying type's
|
||||||
|
behavior as possible.</p>
|
||||||
|
<p>The documentation for these two classes can be found at the following
|
||||||
|
web pages:</p>
|
||||||
|
<ul class="simple">
|
||||||
|
<li><a class="reference external" href="iterator_facade.html"><tt class="docutils literal"><span class="pre">iterator_facade</span></tt></a> (<a class="reference external" href="iterator_facade.pdf">PDF</a>)</li>
|
||||||
|
<li><a class="reference external" href="iterator_adaptor.html"><tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt></a> (<a class="reference external" href="iterator_adaptor.pdf">PDF</a>)</li>
|
||||||
|
</ul>
|
||||||
|
<p>Both <tt class="docutils literal"><span class="pre">iterator_facade</span></tt> and <tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> as well as many of the <a class="reference internal" href="#specialized-adaptors">specialized
|
||||||
|
adaptors</a> mentioned below have been proposed for standardization,
|
||||||
|
and accepted into the first C++ technical report; see our</p>
|
||||||
|
<blockquote>
|
||||||
|
<a class="reference external" href="facade-and-adaptor.html">Standard Proposal For Iterator Facade and Adaptor</a> (<a class="reference external" href="facade-and-adaptor.pdf">PDF</a>)</blockquote>
|
||||||
|
<p>for more details.</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="specialized-adaptors">
|
||||||
|
<h1><a class="toc-backref" href="#id24">Specialized Adaptors</a></h1>
|
||||||
|
<p>The iterator library supplies a useful suite of standard-conforming
|
||||||
|
iterator templates based on the Boost <a class="reference internal" href="#iterator-facade-and-adaptor">iterator facade and adaptor</a>.</p>
|
||||||
|
<ul class="simple">
|
||||||
|
<li><a class="reference external" href="counting_iterator.html"><tt class="docutils literal"><span class="pre">counting_iterator</span></tt></a> (<a class="reference external" href="counting_iterator.pdf">PDF</a>): an iterator over a sequence of consecutive values.
|
||||||
|
Implements a "lazy sequence"</li>
|
||||||
|
<li><a class="reference external" href="filter_iterator.html"><tt class="docutils literal"><span class="pre">filter_iterator</span></tt></a> (<a class="reference external" href="filter_iterator.pdf">PDF</a>): an iterator over the subset of elements of some
|
||||||
|
sequence which satisfy a given predicate</li>
|
||||||
|
<li><a class="reference external" href="function_output_iterator.html"><tt class="docutils literal"><span class="pre">function_output_iterator</span></tt></a> (<a class="reference external" href="function_output_iterator.pdf">PDF</a>): an output iterator wrapping a unary function
|
||||||
|
object; each time an element is written into the dereferenced
|
||||||
|
iterator, it is passed as a parameter to the function object.</li>
|
||||||
|
<li><a class="reference external" href="indirect_iterator.html"><tt class="docutils literal"><span class="pre">indirect_iterator</span></tt></a> (<a class="reference external" href="indirect_iterator.pdf">PDF</a>): an iterator over the objects <em>pointed-to</em> by the
|
||||||
|
elements of some sequence.</li>
|
||||||
|
<li><a class="reference external" href="permutation_iterator.html"><tt class="docutils literal"><span class="pre">permutation_iterator</span></tt></a> (<a class="reference external" href="permutation_iterator.pdf">PDF</a>): an iterator over the elements of some random-access
|
||||||
|
sequence, rearranged according to some sequence of integer indices.</li>
|
||||||
|
<li><a class="reference external" href="reverse_iterator.html"><tt class="docutils literal"><span class="pre">reverse_iterator</span></tt></a> (<a class="reference external" href="reverse_iterator.pdf">PDF</a>): an iterator which traverses the elements of some
|
||||||
|
bidirectional sequence in reverse. Corrects many of the
|
||||||
|
shortcomings of C++98's <tt class="docutils literal"><span class="pre">std::reverse_iterator</span></tt>.</li>
|
||||||
|
<li><a class="reference external" href="../../utility/shared_container_iterator.html"><tt class="docutils literal"><span class="pre">shared_container_iterator</span></tt></a>: an iterator over elements of a container whose
|
||||||
|
lifetime is maintained by a <a class="reference external" href="../../smart_ptr/shared_ptr.htm"><tt class="docutils literal"><span class="pre">shared_ptr</span></tt></a> stored in the iterator.</li>
|
||||||
|
<li><a class="reference external" href="transform_iterator.html"><tt class="docutils literal"><span class="pre">transform_iterator</span></tt></a> (<a class="reference external" href="transform_iterator.pdf">PDF</a>): an iterator over elements which are the result of
|
||||||
|
applying some functional transformation to the elements of an
|
||||||
|
underlying sequence. This component also replaces the old
|
||||||
|
<tt class="docutils literal"><span class="pre">projection_iterator_adaptor</span></tt>.</li>
|
||||||
|
<li><a class="reference external" href="zip_iterator.html"><tt class="docutils literal"><span class="pre">zip_iterator</span></tt></a> (<a class="reference external" href="zip_iterator.pdf">PDF</a>): an iterator over tuples of the elements at corresponding
|
||||||
|
positions of heterogeneous underlying iterators.</li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="iterator-utilities">
|
||||||
|
<h1><a class="toc-backref" href="#id25">Iterator Utilities</a></h1>
|
||||||
|
<div class="section" id="traits">
|
||||||
|
<h2><a class="toc-backref" href="#id26">Traits</a></h2>
|
||||||
|
<ul class="simple">
|
||||||
|
<li><a class="reference external" href="pointee.html"><tt class="docutils literal"><span class="pre">pointee.hpp</span></tt></a> (<a class="reference external" href="pointee.pdf">PDF</a>): Provides the capability to deduce the referent types
|
||||||
|
of pointers, smart pointers and iterators in generic code. Used
|
||||||
|
in <tt class="docutils literal"><span class="pre">indirect_iterator</span></tt>.</li>
|
||||||
|
<li><a class="reference external" href="iterator_traits.html"><tt class="docutils literal"><span class="pre">iterator_traits.hpp</span></tt></a> (<a class="reference external" href="iterator_traits.pdf">PDF</a>): Provides <a class="reference external" href="../../mpl/doc/index.html">MPL</a>-compatible metafunctions which
|
||||||
|
retrieve an iterator's traits. Also corrects for the deficiencies
|
||||||
|
of broken implementations of <tt class="docutils literal"><span class="pre">std::iterator_traits</span></tt>.</li>
|
||||||
|
</ul>
|
||||||
|
<!-- * |interoperable|_ (PDF__): Provides an MPL_\ -compatible metafunction for
|
||||||
|
testing iterator interoperability -->
|
||||||
|
<!-- comment! __ interoperable.pdf -->
|
||||||
|
</div>
|
||||||
|
<div class="section" id="testing-and-concept-checking">
|
||||||
|
<h2><a class="toc-backref" href="#id27">Testing and Concept Checking</a></h2>
|
||||||
|
<ul class="simple">
|
||||||
|
<li><a class="reference external" href="iterator_concepts.html"><tt class="docutils literal"><span class="pre">iterator_concepts.hpp</span></tt></a> (<a class="reference external" href="iterator_concepts.pdf">PDF</a>): Concept checking classes for the new iterator concepts.</li>
|
||||||
|
<li><a class="reference external" href="iterator_archetypes.html"><tt class="docutils literal"><span class="pre">iterator_archetypes.hpp</span></tt></a> (<a class="reference external" href="iterator_archetypes.pdf">PDF</a>): Concept archetype classes for the new iterators concepts.</li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="upgrading-from-the-old-boost-iterator-adaptor-library">
|
||||||
|
<h1><a class="toc-backref" href="#id28">Upgrading from the old Boost Iterator Adaptor Library</a></h1>
|
||||||
|
<p id="upgrading">If you have been using the old Boost Iterator Adaptor library to
|
||||||
|
implement iterators, you probably wrote a <tt class="docutils literal"><span class="pre">Policies</span></tt> class which
|
||||||
|
captures the core operations of your iterator. In the new library
|
||||||
|
design, you'll move those same core operations into the body of the
|
||||||
|
iterator class itself. If you were writing a family of iterators,
|
||||||
|
you probably wrote a <a class="reference external" href="http://www.boost.org/more/generic_programming.html#type_generator">type generator</a> to build the
|
||||||
|
<tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> specialization you needed; in the new library
|
||||||
|
design you don't need a type generator (though may want to keep it
|
||||||
|
around as a compatibility aid for older code) because, due to the
|
||||||
|
use of the Curiously Recurring Template Pattern (CRTP) <a class="citation-reference" href="#cop95" id="id21">[Cop95]</a>,
|
||||||
|
you can now define the iterator class yourself and acquire
|
||||||
|
functionality through inheritance from <tt class="docutils literal"><span class="pre">iterator_facade</span></tt> or
|
||||||
|
<tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt>. As a result, you also get much finer control
|
||||||
|
over how your iterator works: you can add additional constructors,
|
||||||
|
or even override the iterator functionality provided by the
|
||||||
|
library.</p>
|
||||||
|
<p>If you're looking for the old <tt class="docutils literal"><span class="pre">projection_iterator</span></tt> component,
|
||||||
|
its functionality has been merged into <tt class="docutils literal"><span class="pre">transform_iterator</span></tt>: as
|
||||||
|
long as the function object's <tt class="docutils literal"><span class="pre">result_type</span></tt> (or the <tt class="docutils literal"><span class="pre">Reference</span></tt>
|
||||||
|
template argument, if explicitly specified) is a true reference
|
||||||
|
type, <tt class="docutils literal"><span class="pre">transform_iterator</span></tt> will behave like
|
||||||
|
<tt class="docutils literal"><span class="pre">projection_iterator</span></tt> used to.</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="history">
|
||||||
|
<h1><a class="toc-backref" href="#id29">History</a></h1>
|
||||||
|
<p>In 2000 Dave Abrahams was writing an iterator for a container of
|
||||||
|
pointers, which would access the pointed-to elements when
|
||||||
|
dereferenced. Naturally, being a library writer, he decided to
|
||||||
|
generalize the idea and the Boost Iterator Adaptor library was born.
|
||||||
|
Dave was inspired by some writings of Andrei Alexandrescu and chose a
|
||||||
|
policy based design (though he probably didn't capture Andrei's idea
|
||||||
|
very well - there was only one policy class for all the iterator's
|
||||||
|
orthogonal properties). Soon Jeremy Siek realized he would need the
|
||||||
|
library and they worked together to produce a "Boostified" version,
|
||||||
|
which was reviewed and accepted into the library. They wrote a paper
|
||||||
|
and made several important revisions of the code.</p>
|
||||||
|
<p>Eventually, several shortcomings of the older library began to make
|
||||||
|
the need for a rewrite apparent. Dave and Jeremy started working
|
||||||
|
at the Santa Cruz C++ committee meeting in 2002, and had quickly
|
||||||
|
generated a working prototype. At the urging of Mat Marcus, they
|
||||||
|
decided to use the GenVoca/CRTP pattern approach, and moved the
|
||||||
|
policies into the iterator class itself. Thomas Witt expressed
|
||||||
|
interest and became the voice of strict compile-time checking for
|
||||||
|
the project, adding uses of the SFINAE technique to eliminate false
|
||||||
|
converting constructors and operators from the overload set. He
|
||||||
|
also recognized the need for a separate <tt class="docutils literal"><span class="pre">iterator_facade</span></tt>, and
|
||||||
|
factored it out of <tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt>. Finally, after a
|
||||||
|
near-complete rewrite of the prototype, they came up with the
|
||||||
|
library you see today.</p>
|
||||||
|
<table class="docutils citation" frame="void" id="cop95" rules="none">
|
||||||
|
<colgroup><col class="label" /><col /></colgroup>
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><td class="label"><a class="fn-backref" href="#id21">[Cop95]</a></td><td>[Coplien, 1995] Coplien, J., Curiously Recurring Template
|
||||||
|
Patterns, C++ Report, February 1995, pp. 24-27.</td></tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<!-- LocalWords: Abrahams Siek Witt const bool Sutter's WG int UL LI href Lvalue
|
||||||
|
LocalWords: ReadableIterator WritableIterator SwappableIterator cv pre iter
|
||||||
|
LocalWords: ConstantLvalueIterator MutableLvalueIterator CopyConstructible TR
|
||||||
|
LocalWords: ForwardTraversalIterator BidirectionalTraversalIterator lvalue
|
||||||
|
LocalWords: RandomAccessTraversalIterator dereferenceable Incrementable tmp
|
||||||
|
LocalWords: incrementable xxx min prev inplace png oldeqnew AccessTag struct
|
||||||
|
LocalWords: TraversalTag typename lvalues DWA Hmm JGS -->
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<hr class="footer" />
|
||||||
|
<a class="reference external" href="index.rst">View document source</a>.
|
||||||
|
Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
323
doc/index.rst
Normal file
323
doc/index.rst
Normal file
@ -0,0 +1,323 @@
|
|||||||
|
.. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
+++++++++++++++++++++++++++++++++++++++++++++++++
|
||||||
|
The Boost.Iterator Library |(logo)|__
|
||||||
|
+++++++++++++++++++++++++++++++++++++++++++++++++
|
||||||
|
|
||||||
|
.. |(logo)| image:: ../../../boost.png
|
||||||
|
:alt: Boost
|
||||||
|
|
||||||
|
__ ../../../index.htm
|
||||||
|
|
||||||
|
|
||||||
|
-------------------------------------
|
||||||
|
|
||||||
|
|
||||||
|
:Authors: David Abrahams, Jeremy Siek, Thomas Witt
|
||||||
|
:Contact: dave@boost-consulting.com, jsiek@osl.iu.edu, witt@styleadvisor.com
|
||||||
|
:organizations: `Boost Consulting`_, Indiana University `Open Systems
|
||||||
|
Lab`_, `Zephyr Associates, Inc.`_
|
||||||
|
:date: $Date$
|
||||||
|
|
||||||
|
:copyright: Copyright David Abrahams, Jeremy Siek, Thomas Witt 2003.
|
||||||
|
|
||||||
|
.. _`Boost Consulting`: http://www.boost-consulting.com
|
||||||
|
.. _`Open Systems Lab`: http://www.osl.iu.edu
|
||||||
|
.. _`Zephyr Associates, Inc.`: http://www.styleadvisor.com
|
||||||
|
|
||||||
|
:Abstract: The Boost Iterator Library contains two parts. The first
|
||||||
|
is a system of concepts_ which extend the C++ standard
|
||||||
|
iterator requirements. The second is a framework of
|
||||||
|
components for building iterators based on these
|
||||||
|
extended concepts and includes several useful iterator
|
||||||
|
adaptors. The extended iterator concepts have been
|
||||||
|
carefully designed so that old-style iterators
|
||||||
|
can fit in the new concepts and so that new-style
|
||||||
|
iterators will be compatible with old-style algorithms,
|
||||||
|
though algorithms may need to be updated if they want to
|
||||||
|
take full advantage of the new-style iterator
|
||||||
|
capabilities. Several components of this library have
|
||||||
|
been accepted into the C++ standard technical report.
|
||||||
|
The components of the Boost Iterator Library replace the
|
||||||
|
older Boost Iterator Adaptor Library.
|
||||||
|
|
||||||
|
.. _concepts: http://www.boost.org/more/generic_programming.html#concept
|
||||||
|
|
||||||
|
.. contents:: **Table of Contents**
|
||||||
|
|
||||||
|
|
||||||
|
-------------------------------------
|
||||||
|
|
||||||
|
|
||||||
|
=====================
|
||||||
|
New-Style Iterators
|
||||||
|
=====================
|
||||||
|
|
||||||
|
The iterator categories defined in C++98 are extremely limiting
|
||||||
|
because they bind together two orthogonal concepts: traversal and
|
||||||
|
element access. For example, because a random access iterator is
|
||||||
|
required to return a reference (and not a proxy) when dereferenced,
|
||||||
|
it is impossible to capture the capabilities of
|
||||||
|
``vector<bool>::iterator`` using the C++98 categories. This is the
|
||||||
|
infamous "``vector<bool>`` is not a container, and its iterators
|
||||||
|
aren't random access iterators", debacle about which Herb Sutter
|
||||||
|
wrote two papers for the standards comittee (n1185_ and n1211_),
|
||||||
|
and a `Guru of the Week`__. New-style iterators go well beyond
|
||||||
|
patching up ``vector<bool>``, though: there are lots of other
|
||||||
|
iterators already in use which can't be adequately represented by
|
||||||
|
the existing concepts. For details about the new iterator
|
||||||
|
concepts, see our
|
||||||
|
|
||||||
|
.. _n1185: http://www.gotw.ca/publications/N1185.pdf
|
||||||
|
.. _n1211: http://www.gotw.ca/publications/N1211.pdf
|
||||||
|
__ http://www.gotw.ca/gotw/050.htm
|
||||||
|
|
||||||
|
|
||||||
|
`Standard Proposal For New-Style Iterators`__ (PDF__)
|
||||||
|
|
||||||
|
__ new-iter-concepts.html
|
||||||
|
__ new-iter-concepts.pdf
|
||||||
|
|
||||||
|
=============================
|
||||||
|
Iterator Facade and Adaptor
|
||||||
|
=============================
|
||||||
|
|
||||||
|
Writing standard-conforming iterators is tricky, but the need comes
|
||||||
|
up often. In order to ease the implementation of new iterators,
|
||||||
|
the Boost.Iterator library provides the |facade| class template,
|
||||||
|
which implements many useful defaults and compile-time checks
|
||||||
|
designed to help the iterator author ensure that his iterator is
|
||||||
|
correct.
|
||||||
|
|
||||||
|
It is also common to define a new iterator that is similar to some
|
||||||
|
underlying iterator or iterator-like type, but that modifies some
|
||||||
|
aspect of the underlying type's behavior. For that purpose, the
|
||||||
|
library supplies the |adaptor| class template, which is specially
|
||||||
|
designed to take advantage of as much of the underlying type's
|
||||||
|
behavior as possible.
|
||||||
|
|
||||||
|
The documentation for these two classes can be found at the following
|
||||||
|
web pages:
|
||||||
|
|
||||||
|
* |facade|_ (PDF__)
|
||||||
|
|
||||||
|
* |adaptor|_ (PDF__)
|
||||||
|
|
||||||
|
|
||||||
|
.. |facade| replace:: ``iterator_facade``
|
||||||
|
.. _facade: iterator_facade.html
|
||||||
|
__ iterator_facade.pdf
|
||||||
|
|
||||||
|
.. |adaptor| replace:: ``iterator_adaptor``
|
||||||
|
.. _adaptor: iterator_adaptor.html
|
||||||
|
__ iterator_adaptor.pdf
|
||||||
|
|
||||||
|
Both |facade| and |adaptor| as well as many of the `specialized
|
||||||
|
adaptors`_ mentioned below have been proposed for standardization,
|
||||||
|
and accepted into the first C++ technical report; see our
|
||||||
|
|
||||||
|
`Standard Proposal For Iterator Facade and Adaptor`__ (PDF__)
|
||||||
|
|
||||||
|
for more details.
|
||||||
|
|
||||||
|
__ facade-and-adaptor.html
|
||||||
|
__ facade-and-adaptor.pdf
|
||||||
|
|
||||||
|
======================
|
||||||
|
Specialized Adaptors
|
||||||
|
======================
|
||||||
|
|
||||||
|
The iterator library supplies a useful suite of standard-conforming
|
||||||
|
iterator templates based on the Boost `iterator facade and adaptor`_.
|
||||||
|
|
||||||
|
* |counting|_ (PDF__): an iterator over a sequence of consecutive values.
|
||||||
|
Implements a "lazy sequence"
|
||||||
|
|
||||||
|
* |filter|_ (PDF__): an iterator over the subset of elements of some
|
||||||
|
sequence which satisfy a given predicate
|
||||||
|
|
||||||
|
* |function|_ (PDF__): an output iterator wrapping a unary function
|
||||||
|
object; each time an element is written into the dereferenced
|
||||||
|
iterator, it is passed as a parameter to the function object.
|
||||||
|
|
||||||
|
* |indirect|_ (PDF__): an iterator over the objects *pointed-to* by the
|
||||||
|
elements of some sequence.
|
||||||
|
|
||||||
|
* |permutation|_ (PDF__): an iterator over the elements of some random-access
|
||||||
|
sequence, rearranged according to some sequence of integer indices.
|
||||||
|
|
||||||
|
* |reverse|_ (PDF__): an iterator which traverses the elements of some
|
||||||
|
bidirectional sequence in reverse. Corrects many of the
|
||||||
|
shortcomings of C++98's ``std::reverse_iterator``.
|
||||||
|
|
||||||
|
* |shared|_: an iterator over elements of a container whose
|
||||||
|
lifetime is maintained by a |shared_ptr|_ stored in the iterator.
|
||||||
|
|
||||||
|
* |transform|_ (PDF__): an iterator over elements which are the result of
|
||||||
|
applying some functional transformation to the elements of an
|
||||||
|
underlying sequence. This component also replaces the old
|
||||||
|
``projection_iterator_adaptor``.
|
||||||
|
|
||||||
|
* |zip|_ (PDF__): an iterator over tuples of the elements at corresponding
|
||||||
|
positions of heterogeneous underlying iterators.
|
||||||
|
|
||||||
|
.. |counting| replace:: ``counting_iterator``
|
||||||
|
.. _counting: counting_iterator.html
|
||||||
|
__ counting_iterator.pdf
|
||||||
|
|
||||||
|
.. |filter| replace:: ``filter_iterator``
|
||||||
|
.. _filter: filter_iterator.html
|
||||||
|
__ filter_iterator.pdf
|
||||||
|
|
||||||
|
.. |function| replace:: ``function_output_iterator``
|
||||||
|
.. _function: function_output_iterator.html
|
||||||
|
__ function_output_iterator.pdf
|
||||||
|
|
||||||
|
.. |indirect| replace:: ``indirect_iterator``
|
||||||
|
.. _indirect: indirect_iterator.html
|
||||||
|
__ indirect_iterator.pdf
|
||||||
|
|
||||||
|
.. |permutation| replace:: ``permutation_iterator``
|
||||||
|
.. _permutation: permutation_iterator.html
|
||||||
|
__ permutation_iterator.pdf
|
||||||
|
|
||||||
|
.. |reverse| replace:: ``reverse_iterator``
|
||||||
|
.. _reverse: reverse_iterator.html
|
||||||
|
__ reverse_iterator.pdf
|
||||||
|
|
||||||
|
.. |shared| replace:: ``shared_container_iterator``
|
||||||
|
.. _shared: ../../utility/shared_container_iterator.html
|
||||||
|
|
||||||
|
.. |transform| replace:: ``transform_iterator``
|
||||||
|
.. _transform: transform_iterator.html
|
||||||
|
__ transform_iterator.pdf
|
||||||
|
|
||||||
|
.. |zip| replace:: ``zip_iterator``
|
||||||
|
.. _zip: zip_iterator.html
|
||||||
|
__ zip_iterator.pdf
|
||||||
|
|
||||||
|
.. |shared_ptr| replace:: ``shared_ptr``
|
||||||
|
.. _shared_ptr: ../../smart_ptr/shared_ptr.htm
|
||||||
|
|
||||||
|
====================
|
||||||
|
Iterator Utilities
|
||||||
|
====================
|
||||||
|
|
||||||
|
Traits
|
||||||
|
------
|
||||||
|
|
||||||
|
* |pointee|_ (PDF__): Provides the capability to deduce the referent types
|
||||||
|
of pointers, smart pointers and iterators in generic code. Used
|
||||||
|
in |indirect|.
|
||||||
|
|
||||||
|
* |iterator_traits|_ (PDF__): Provides MPL_\ -compatible metafunctions which
|
||||||
|
retrieve an iterator's traits. Also corrects for the deficiencies
|
||||||
|
of broken implementations of ``std::iterator_traits``.
|
||||||
|
|
||||||
|
.. * |interoperable|_ (PDF__): Provides an MPL_\ -compatible metafunction for
|
||||||
|
testing iterator interoperability
|
||||||
|
|
||||||
|
.. |pointee| replace:: ``pointee.hpp``
|
||||||
|
.. _pointee: pointee.html
|
||||||
|
__ pointee.pdf
|
||||||
|
|
||||||
|
.. |iterator_traits| replace:: ``iterator_traits.hpp``
|
||||||
|
.. _iterator_traits: iterator_traits.html
|
||||||
|
__ iterator_traits.pdf
|
||||||
|
|
||||||
|
.. |interoperable| replace:: ``interoperable.hpp``
|
||||||
|
.. _interoperable: interoperable.html
|
||||||
|
.. comment! __ interoperable.pdf
|
||||||
|
|
||||||
|
.. _MPL: ../../mpl/doc/index.html
|
||||||
|
|
||||||
|
Testing and Concept Checking
|
||||||
|
----------------------------
|
||||||
|
|
||||||
|
* |iterator_concepts|_ (PDF__): Concept checking classes for the new iterator concepts.
|
||||||
|
|
||||||
|
* |iterator_archetypes|_ (PDF__): Concept archetype classes for the new iterators concepts.
|
||||||
|
|
||||||
|
.. |iterator_concepts| replace:: ``iterator_concepts.hpp``
|
||||||
|
.. _iterator_concepts: iterator_concepts.html
|
||||||
|
__ iterator_concepts.pdf
|
||||||
|
|
||||||
|
.. |iterator_archetypes| replace:: ``iterator_archetypes.hpp``
|
||||||
|
.. _iterator_archetypes: iterator_archetypes.html
|
||||||
|
__ iterator_archetypes.pdf
|
||||||
|
|
||||||
|
=======================================================
|
||||||
|
Upgrading from the old Boost Iterator Adaptor Library
|
||||||
|
=======================================================
|
||||||
|
|
||||||
|
.. _Upgrading:
|
||||||
|
|
||||||
|
If you have been using the old Boost Iterator Adaptor library to
|
||||||
|
implement iterators, you probably wrote a ``Policies`` class which
|
||||||
|
captures the core operations of your iterator. In the new library
|
||||||
|
design, you'll move those same core operations into the body of the
|
||||||
|
iterator class itself. If you were writing a family of iterators,
|
||||||
|
you probably wrote a `type generator`_ to build the
|
||||||
|
``iterator_adaptor`` specialization you needed; in the new library
|
||||||
|
design you don't need a type generator (though may want to keep it
|
||||||
|
around as a compatibility aid for older code) because, due to the
|
||||||
|
use of the Curiously Recurring Template Pattern (CRTP) [Cop95]_,
|
||||||
|
you can now define the iterator class yourself and acquire
|
||||||
|
functionality through inheritance from ``iterator_facade`` or
|
||||||
|
``iterator_adaptor``. As a result, you also get much finer control
|
||||||
|
over how your iterator works: you can add additional constructors,
|
||||||
|
or even override the iterator functionality provided by the
|
||||||
|
library.
|
||||||
|
|
||||||
|
.. _`type generator`: http://www.boost.org/more/generic_programming.html#type_generator
|
||||||
|
|
||||||
|
If you're looking for the old ``projection_iterator`` component,
|
||||||
|
its functionality has been merged into ``transform_iterator``: as
|
||||||
|
long as the function object's ``result_type`` (or the ``Reference``
|
||||||
|
template argument, if explicitly specified) is a true reference
|
||||||
|
type, ``transform_iterator`` will behave like
|
||||||
|
``projection_iterator`` used to.
|
||||||
|
|
||||||
|
=========
|
||||||
|
History
|
||||||
|
=========
|
||||||
|
|
||||||
|
In 2000 Dave Abrahams was writing an iterator for a container of
|
||||||
|
pointers, which would access the pointed-to elements when
|
||||||
|
dereferenced. Naturally, being a library writer, he decided to
|
||||||
|
generalize the idea and the Boost Iterator Adaptor library was born.
|
||||||
|
Dave was inspired by some writings of Andrei Alexandrescu and chose a
|
||||||
|
policy based design (though he probably didn't capture Andrei's idea
|
||||||
|
very well - there was only one policy class for all the iterator's
|
||||||
|
orthogonal properties). Soon Jeremy Siek realized he would need the
|
||||||
|
library and they worked together to produce a "Boostified" version,
|
||||||
|
which was reviewed and accepted into the library. They wrote a paper
|
||||||
|
and made several important revisions of the code.
|
||||||
|
|
||||||
|
Eventually, several shortcomings of the older library began to make
|
||||||
|
the need for a rewrite apparent. Dave and Jeremy started working
|
||||||
|
at the Santa Cruz C++ committee meeting in 2002, and had quickly
|
||||||
|
generated a working prototype. At the urging of Mat Marcus, they
|
||||||
|
decided to use the GenVoca/CRTP pattern approach, and moved the
|
||||||
|
policies into the iterator class itself. Thomas Witt expressed
|
||||||
|
interest and became the voice of strict compile-time checking for
|
||||||
|
the project, adding uses of the SFINAE technique to eliminate false
|
||||||
|
converting constructors and operators from the overload set. He
|
||||||
|
also recognized the need for a separate ``iterator_facade``, and
|
||||||
|
factored it out of ``iterator_adaptor``. Finally, after a
|
||||||
|
near-complete rewrite of the prototype, they came up with the
|
||||||
|
library you see today.
|
||||||
|
|
||||||
|
.. [Cop95] [Coplien, 1995] Coplien, J., Curiously Recurring Template
|
||||||
|
Patterns, C++ Report, February 1995, pp. 24-27.
|
||||||
|
|
||||||
|
..
|
||||||
|
LocalWords: Abrahams Siek Witt const bool Sutter's WG int UL LI href Lvalue
|
||||||
|
LocalWords: ReadableIterator WritableIterator SwappableIterator cv pre iter
|
||||||
|
LocalWords: ConstantLvalueIterator MutableLvalueIterator CopyConstructible TR
|
||||||
|
LocalWords: ForwardTraversalIterator BidirectionalTraversalIterator lvalue
|
||||||
|
LocalWords: RandomAccessTraversalIterator dereferenceable Incrementable tmp
|
||||||
|
LocalWords: incrementable xxx min prev inplace png oldeqnew AccessTag struct
|
||||||
|
LocalWords: TraversalTag typename lvalues DWA Hmm JGS
|
345
doc/indirect_iterator.html
Normal file
345
doc/indirect_iterator.html
Normal file
@ -0,0 +1,345 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" />
|
||||||
|
<title>Indirect Iterator</title>
|
||||||
|
<meta name="author" content="David Abrahams, Jeremy Siek, Thomas Witt" />
|
||||||
|
<meta name="organization" content="Boost Consulting, Indiana University Open Systems Lab, University of Hanover Institute for Transport Railway Operation and Construction" />
|
||||||
|
<meta name="date" content="2006-09-11" />
|
||||||
|
<meta name="copyright" content="Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003." />
|
||||||
|
<link rel="stylesheet" href="../../../rst.css" type="text/css" />
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="indirect-iterator">
|
||||||
|
<h1 class="title">Indirect Iterator</h1>
|
||||||
|
<table class="docinfo" frame="void" rules="none">
|
||||||
|
<col class="docinfo-name" />
|
||||||
|
<col class="docinfo-content" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><th class="docinfo-name">Author:</th>
|
||||||
|
<td>David Abrahams, Jeremy Siek, Thomas Witt</td></tr>
|
||||||
|
<tr><th class="docinfo-name">Contact:</th>
|
||||||
|
<td><a class="first reference external" href="mailto:dave@boost-consulting.com">dave@boost-consulting.com</a>, <a class="reference external" href="mailto:jsiek@osl.iu.edu">jsiek@osl.iu.edu</a>, <a class="last reference external" href="mailto:witt@ive.uni-hannover.de">witt@ive.uni-hannover.de</a></td></tr>
|
||||||
|
<tr><th class="docinfo-name">Organization:</th>
|
||||||
|
<td><a class="first reference external" href="http://www.boost-consulting.com">Boost Consulting</a>, Indiana University <a class="reference external" href="http://www.osl.iu.edu">Open Systems
|
||||||
|
Lab</a>, University of Hanover <a class="last reference external" href="http://www.ive.uni-hannover.de">Institute for Transport
|
||||||
|
Railway Operation and Construction</a></td></tr>
|
||||||
|
<tr><th class="docinfo-name">Date:</th>
|
||||||
|
<td>2006-09-11</td></tr>
|
||||||
|
<tr><th class="docinfo-name">Copyright:</th>
|
||||||
|
<td>Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003.</td></tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<!-- Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">abstract:</th><td class="field-body"><!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<tt class="docutils literal"><span class="pre">indirect_iterator</span></tt> adapts an iterator by applying an
|
||||||
|
<em>extra</em> dereference inside of <tt class="docutils literal"><span class="pre">operator*()</span></tt>. For example, this
|
||||||
|
iterator adaptor makes it possible to view a container of pointers
|
||||||
|
(e.g. <tt class="docutils literal"><span class="pre">list<foo*></span></tt>) as if it were a container of the pointed-to type
|
||||||
|
(e.g. <tt class="docutils literal"><span class="pre">list<foo></span></tt>). <tt class="docutils literal"><span class="pre">indirect_iterator</span></tt> depends on two
|
||||||
|
auxiliary traits, <tt class="docutils literal"><span class="pre">pointee</span></tt> and <tt class="docutils literal"><span class="pre">indirect_reference</span></tt>, to
|
||||||
|
provide support for underlying iterators whose <tt class="docutils literal"><span class="pre">value_type</span></tt> is
|
||||||
|
not an iterator.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<div class="contents topic" id="table-of-contents">
|
||||||
|
<p class="topic-title first">Table of Contents</p>
|
||||||
|
<ul class="simple">
|
||||||
|
<li><a class="reference internal" href="#indirect-iterator-synopsis" id="id2"><tt class="docutils literal"><span class="pre">indirect_iterator</span></tt> synopsis</a></li>
|
||||||
|
<li><a class="reference internal" href="#indirect-iterator-requirements" id="id3"><tt class="docutils literal"><span class="pre">indirect_iterator</span></tt> requirements</a></li>
|
||||||
|
<li><a class="reference internal" href="#indirect-iterator-models" id="id4"><tt class="docutils literal"><span class="pre">indirect_iterator</span></tt> models</a></li>
|
||||||
|
<li><a class="reference internal" href="#indirect-iterator-operations" id="id5"><tt class="docutils literal"><span class="pre">indirect_iterator</span></tt> operations</a></li>
|
||||||
|
<li><a class="reference internal" href="#example" id="id6">Example</a></li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="indirect-iterator-synopsis">
|
||||||
|
<h1><a class="toc-backref" href="#id2"><tt class="docutils literal"><span class="pre">indirect_iterator</span></tt> synopsis</a></h1>
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<pre class="literal-block">
|
||||||
|
template <
|
||||||
|
class Iterator
|
||||||
|
, class Value = use_default
|
||||||
|
, class CategoryOrTraversal = use_default
|
||||||
|
, class Reference = use_default
|
||||||
|
, class Difference = use_default
|
||||||
|
>
|
||||||
|
class indirect_iterator
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
typedef /* see below */ value_type;
|
||||||
|
typedef /* see below */ reference;
|
||||||
|
typedef /* see below */ pointer;
|
||||||
|
typedef /* see below */ difference_type;
|
||||||
|
typedef /* see below */ iterator_category;
|
||||||
|
|
||||||
|
indirect_iterator();
|
||||||
|
indirect_iterator(Iterator x);
|
||||||
|
|
||||||
|
template <
|
||||||
|
class Iterator2, class Value2, class Category2
|
||||||
|
, class Reference2, class Difference2
|
||||||
|
>
|
||||||
|
indirect_iterator(
|
||||||
|
indirect_iterator<
|
||||||
|
Iterator2, Value2, Category2, Reference2, Difference2
|
||||||
|
> const& y
|
||||||
|
, typename enable_if_convertible<Iterator2, Iterator>::type* = 0 // exposition
|
||||||
|
);
|
||||||
|
|
||||||
|
Iterator const& base() const;
|
||||||
|
reference operator*() const;
|
||||||
|
indirect_iterator& operator++();
|
||||||
|
indirect_iterator& operator--();
|
||||||
|
private:
|
||||||
|
Iterator m_iterator; // exposition
|
||||||
|
};
|
||||||
|
</pre>
|
||||||
|
<p>The member types of <tt class="docutils literal"><span class="pre">indirect_iterator</span></tt> are defined according to
|
||||||
|
the following pseudo-code, where <tt class="docutils literal"><span class="pre">V</span></tt> is
|
||||||
|
<tt class="docutils literal"><span class="pre">iterator_traits<Iterator>::value_type</span></tt></p>
|
||||||
|
<pre class="literal-block">
|
||||||
|
if (Value is use_default) then
|
||||||
|
typedef remove_const<pointee<V>::type>::type value_type;
|
||||||
|
else
|
||||||
|
typedef remove_const<Value>::type value_type;
|
||||||
|
|
||||||
|
if (Reference is use_default) then
|
||||||
|
if (Value is use_default) then
|
||||||
|
typedef indirect_reference<V>::type reference;
|
||||||
|
else
|
||||||
|
typedef Value& reference;
|
||||||
|
else
|
||||||
|
typedef Reference reference;
|
||||||
|
|
||||||
|
if (Value is use_default) then
|
||||||
|
typedef pointee<V>::type* pointer;
|
||||||
|
else
|
||||||
|
typedef Value* pointer;
|
||||||
|
|
||||||
|
if (Difference is use_default)
|
||||||
|
typedef iterator_traits<Iterator>::difference_type difference_type;
|
||||||
|
else
|
||||||
|
typedef Difference difference_type;
|
||||||
|
|
||||||
|
if (CategoryOrTraversal is use_default)
|
||||||
|
typedef <em>iterator-category</em> (
|
||||||
|
iterator_traversal<Iterator>::type,``reference``,``value_type``
|
||||||
|
) iterator_category;
|
||||||
|
else
|
||||||
|
typedef <em>iterator-category</em> (
|
||||||
|
CategoryOrTraversal,``reference``,``value_type``
|
||||||
|
) iterator_category;
|
||||||
|
</pre>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="indirect-iterator-requirements">
|
||||||
|
<h1><a class="toc-backref" href="#id3"><tt class="docutils literal"><span class="pre">indirect_iterator</span></tt> requirements</a></h1>
|
||||||
|
<p>The expression <tt class="docutils literal"><span class="pre">*v</span></tt>, where <tt class="docutils literal"><span class="pre">v</span></tt> is an object of
|
||||||
|
<tt class="docutils literal"><span class="pre">iterator_traits<Iterator>::value_type</span></tt>, shall be valid
|
||||||
|
expression and convertible to <tt class="docutils literal"><span class="pre">reference</span></tt>. <tt class="docutils literal"><span class="pre">Iterator</span></tt> shall
|
||||||
|
model the traversal concept indicated by <tt class="docutils literal"><span class="pre">iterator_category</span></tt>.
|
||||||
|
<tt class="docutils literal"><span class="pre">Value</span></tt>, <tt class="docutils literal"><span class="pre">Reference</span></tt>, and <tt class="docutils literal"><span class="pre">Difference</span></tt> shall be chosen so
|
||||||
|
that <tt class="docutils literal"><span class="pre">value_type</span></tt>, <tt class="docutils literal"><span class="pre">reference</span></tt>, and <tt class="docutils literal"><span class="pre">difference_type</span></tt> meet
|
||||||
|
the requirements indicated by <tt class="docutils literal"><span class="pre">iterator_category</span></tt>.</p>
|
||||||
|
<p>[Note: there are further requirements on the
|
||||||
|
<tt class="docutils literal"><span class="pre">iterator_traits<Iterator>::value_type</span></tt> if the <tt class="docutils literal"><span class="pre">Value</span></tt>
|
||||||
|
parameter is not <tt class="docutils literal"><span class="pre">use_default</span></tt>, as implied by the algorithm for
|
||||||
|
deducing the default for the <tt class="docutils literal"><span class="pre">value_type</span></tt> member.]</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="indirect-iterator-models">
|
||||||
|
<h1><a class="toc-backref" href="#id4"><tt class="docutils literal"><span class="pre">indirect_iterator</span></tt> models</a></h1>
|
||||||
|
<p>In addition to the concepts indicated by <tt class="docutils literal"><span class="pre">iterator_category</span></tt>
|
||||||
|
and by <tt class="docutils literal"><span class="pre">iterator_traversal<indirect_iterator>::type</span></tt>, a
|
||||||
|
specialization of <tt class="docutils literal"><span class="pre">indirect_iterator</span></tt> models the following
|
||||||
|
concepts, Where <tt class="docutils literal"><span class="pre">v</span></tt> is an object of
|
||||||
|
<tt class="docutils literal"><span class="pre">iterator_traits<Iterator>::value_type</span></tt>:</p>
|
||||||
|
<blockquote>
|
||||||
|
<ul class="simple">
|
||||||
|
<li>Readable Iterator if <tt class="docutils literal"><span class="pre">reference(*v)</span></tt> is convertible to
|
||||||
|
<tt class="docutils literal"><span class="pre">value_type</span></tt>.</li>
|
||||||
|
<li>Writable Iterator if <tt class="docutils literal"><span class="pre">reference(*v)</span> <span class="pre">=</span> <span class="pre">t</span></tt> is a valid
|
||||||
|
expression (where <tt class="docutils literal"><span class="pre">t</span></tt> is an object of type
|
||||||
|
<tt class="docutils literal"><span class="pre">indirect_iterator::value_type</span></tt>)</li>
|
||||||
|
<li>Lvalue Iterator if <tt class="docutils literal"><span class="pre">reference</span></tt> is a reference type.</li>
|
||||||
|
</ul>
|
||||||
|
</blockquote>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">indirect_iterator<X,V1,C1,R1,D1></span></tt> is interoperable with
|
||||||
|
<tt class="docutils literal"><span class="pre">indirect_iterator<Y,V2,C2,R2,D2></span></tt> if and only if <tt class="docutils literal"><span class="pre">X</span></tt> is
|
||||||
|
interoperable with <tt class="docutils literal"><span class="pre">Y</span></tt>.</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="indirect-iterator-operations">
|
||||||
|
<h1><a class="toc-backref" href="#id5"><tt class="docutils literal"><span class="pre">indirect_iterator</span></tt> operations</a></h1>
|
||||||
|
<p>In addition to the operations required by the concepts described
|
||||||
|
above, specializations of <tt class="docutils literal"><span class="pre">indirect_iterator</span></tt> provide the
|
||||||
|
following operations.</p>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">indirect_iterator();</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Requires:</th><td class="field-body"><tt class="docutils literal"><span class="pre">Iterator</span></tt> must be Default Constructible.</td>
|
||||||
|
</tr>
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body">Constructs an instance of <tt class="docutils literal"><span class="pre">indirect_iterator</span></tt> with
|
||||||
|
a default-constructed <tt class="docutils literal"><span class="pre">m_iterator</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">indirect_iterator(Iterator</span> <span class="pre">x);</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body">Constructs an instance of <tt class="docutils literal"><span class="pre">indirect_iterator</span></tt> with
|
||||||
|
<tt class="docutils literal"><span class="pre">m_iterator</span></tt> copy constructed from <tt class="docutils literal"><span class="pre">x</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<pre class="literal-block">
|
||||||
|
template <
|
||||||
|
class Iterator2, class Value2, unsigned Access, class Traversal
|
||||||
|
, class Reference2, class Difference2
|
||||||
|
>
|
||||||
|
indirect_iterator(
|
||||||
|
indirect_iterator<
|
||||||
|
Iterator2, Value2, Access, Traversal, Reference2, Difference2
|
||||||
|
> const& y
|
||||||
|
, typename enable_if_convertible<Iterator2, Iterator>::type* = 0 // exposition
|
||||||
|
);
|
||||||
|
</pre>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Requires:</th><td class="field-body"><tt class="docutils literal"><span class="pre">Iterator2</span></tt> is implicitly convertible to <tt class="docutils literal"><span class="pre">Iterator</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body">Constructs an instance of <tt class="docutils literal"><span class="pre">indirect_iterator</span></tt> whose
|
||||||
|
<tt class="docutils literal"><span class="pre">m_iterator</span></tt> subobject is constructed from <tt class="docutils literal"><span class="pre">y.base()</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">Iterator</span> <span class="pre">const&</span> <span class="pre">base()</span> <span class="pre">const;</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">m_iterator</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">reference</span> <span class="pre">operator*()</span> <span class="pre">const;</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">**m_iterator</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">indirect_iterator&</span> <span class="pre">operator++();</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body"><tt class="docutils literal"><span class="pre">++m_iterator</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">*this</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">indirect_iterator&</span> <span class="pre">operator--();</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body"><tt class="docutils literal"><span class="pre">--m_iterator</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">*this</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
</div>
|
||||||
|
<div class="section" id="example">
|
||||||
|
<h1><a class="toc-backref" href="#id6">Example</a></h1>
|
||||||
|
<p>This example prints an array of characters, using
|
||||||
|
<tt class="docutils literal"><span class="pre">indirect_iterator</span></tt> to access the array of characters through an
|
||||||
|
array of pointers. Next <tt class="docutils literal"><span class="pre">indirect_iterator</span></tt> is used with the
|
||||||
|
<tt class="docutils literal"><span class="pre">transform</span></tt> algorithm to copy the characters (incremented by one) to
|
||||||
|
another array. A constant indirect iterator is used for the source and
|
||||||
|
a mutable indirect iterator is used for the destination. The last part
|
||||||
|
of the example prints the original array of characters, but this time
|
||||||
|
using the <tt class="docutils literal"><span class="pre">make_indirect_iterator</span></tt> helper function.</p>
|
||||||
|
<pre class="literal-block">
|
||||||
|
char characters[] = "abcdefg";
|
||||||
|
const int N = sizeof(characters)/sizeof(char) - 1; // -1 since characters has a null char
|
||||||
|
char* pointers_to_chars[N]; // at the end.
|
||||||
|
for (int i = 0; i < N; ++i)
|
||||||
|
pointers_to_chars[i] = &characters[i];
|
||||||
|
|
||||||
|
// Example of using indirect_iterator
|
||||||
|
|
||||||
|
boost::indirect_iterator<char**, char>
|
||||||
|
indirect_first(pointers_to_chars), indirect_last(pointers_to_chars + N);
|
||||||
|
|
||||||
|
std::copy(indirect_first, indirect_last, std::ostream_iterator<char>(std::cout, ","));
|
||||||
|
std::cout << std::endl;
|
||||||
|
|
||||||
|
|
||||||
|
// Example of making mutable and constant indirect iterators
|
||||||
|
|
||||||
|
char mutable_characters[N];
|
||||||
|
char* pointers_to_mutable_chars[N];
|
||||||
|
for (int j = 0; j < N; ++j)
|
||||||
|
pointers_to_mutable_chars[j] = &mutable_characters[j];
|
||||||
|
|
||||||
|
boost::indirect_iterator<char* const*> mutable_indirect_first(pointers_to_mutable_chars),
|
||||||
|
mutable_indirect_last(pointers_to_mutable_chars + N);
|
||||||
|
boost::indirect_iterator<char* const*, char const> const_indirect_first(pointers_to_chars),
|
||||||
|
const_indirect_last(pointers_to_chars + N);
|
||||||
|
|
||||||
|
std::transform(const_indirect_first, const_indirect_last,
|
||||||
|
mutable_indirect_first, std::bind1st(std::plus<char>(), 1));
|
||||||
|
|
||||||
|
std::copy(mutable_indirect_first, mutable_indirect_last,
|
||||||
|
std::ostream_iterator<char>(std::cout, ","));
|
||||||
|
std::cout << std::endl;
|
||||||
|
|
||||||
|
|
||||||
|
// Example of using make_indirect_iterator()
|
||||||
|
|
||||||
|
std::copy(boost::make_indirect_iterator(pointers_to_chars),
|
||||||
|
boost::make_indirect_iterator(pointers_to_chars + N),
|
||||||
|
std::ostream_iterator<char>(std::cout, ","));
|
||||||
|
std::cout << std::endl;
|
||||||
|
</pre>
|
||||||
|
<p>The output is:</p>
|
||||||
|
<pre class="literal-block">
|
||||||
|
a,b,c,d,e,f,g,
|
||||||
|
b,c,d,e,f,g,h,
|
||||||
|
a,b,c,d,e,f,g,
|
||||||
|
</pre>
|
||||||
|
<p>The source code for this example can be found <a class="reference external" href="../example/indirect_iterator_example.cpp">here</a>.</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<hr class="footer" />
|
||||||
|
<a class="reference external" href="indirect_iterator.rst">View document source</a>.
|
||||||
|
Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
BIN
doc/indirect_iterator.pdf
Normal file
BIN
doc/indirect_iterator.pdf
Normal file
Binary file not shown.
34
doc/indirect_iterator.rst
Normal file
34
doc/indirect_iterator.rst
Normal file
@ -0,0 +1,34 @@
|
|||||||
|
.. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
+++++++++++++++++++
|
||||||
|
Indirect Iterator
|
||||||
|
+++++++++++++++++++
|
||||||
|
|
||||||
|
:Author: David Abrahams, Jeremy Siek, Thomas Witt
|
||||||
|
:Contact: dave@boost-consulting.com, jsiek@osl.iu.edu, witt@ive.uni-hannover.de
|
||||||
|
:organization: `Boost Consulting`_, Indiana University `Open Systems
|
||||||
|
Lab`_, University of Hanover `Institute for Transport
|
||||||
|
Railway Operation and Construction`_
|
||||||
|
:date: $Date$
|
||||||
|
:copyright: Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003.
|
||||||
|
|
||||||
|
.. _`Boost Consulting`: http://www.boost-consulting.com
|
||||||
|
.. _`Open Systems Lab`: http://www.osl.iu.edu
|
||||||
|
.. _`Institute for Transport Railway Operation and Construction`: http://www.ive.uni-hannover.de
|
||||||
|
|
||||||
|
:abstract:
|
||||||
|
|
||||||
|
.. include:: indirect_iterator_abstract.rst
|
||||||
|
|
||||||
|
.. contents:: Table of Contents
|
||||||
|
|
||||||
|
``indirect_iterator`` synopsis
|
||||||
|
..............................
|
||||||
|
|
||||||
|
.. include:: indirect_iterator_ref.rst
|
||||||
|
.. include:: indirect_iterator_eg.rst
|
||||||
|
|
||||||
|
.. _iterator-category: iterator_facade.html#iterator-category
|
||||||
|
.. |iterator-category| replace:: *iterator-category*
|
15
doc/indirect_iterator_abstract.rst
Normal file
15
doc/indirect_iterator_abstract.rst
Normal file
@ -0,0 +1,15 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
``indirect_iterator`` adapts an iterator by applying an
|
||||||
|
*extra* dereference inside of ``operator*()``. For example, this
|
||||||
|
iterator adaptor makes it possible to view a container of pointers
|
||||||
|
(e.g. ``list<foo*>``) as if it were a container of the pointed-to type
|
||||||
|
(e.g. ``list<foo>``). ``indirect_iterator`` depends on two
|
||||||
|
auxiliary traits, ``pointee`` and ``indirect_reference``, to
|
||||||
|
provide support for underlying iterators whose ``value_type`` is
|
||||||
|
not an iterator.
|
||||||
|
|
||||||
|
|
||||||
|
|
73
doc/indirect_iterator_eg.rst
Normal file
73
doc/indirect_iterator_eg.rst
Normal file
@ -0,0 +1,73 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
Example
|
||||||
|
.......
|
||||||
|
|
||||||
|
This example prints an array of characters, using
|
||||||
|
``indirect_iterator`` to access the array of characters through an
|
||||||
|
array of pointers. Next ``indirect_iterator`` is used with the
|
||||||
|
``transform`` algorithm to copy the characters (incremented by one) to
|
||||||
|
another array. A constant indirect iterator is used for the source and
|
||||||
|
a mutable indirect iterator is used for the destination. The last part
|
||||||
|
of the example prints the original array of characters, but this time
|
||||||
|
using the ``make_indirect_iterator`` helper function.
|
||||||
|
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
char characters[] = "abcdefg";
|
||||||
|
const int N = sizeof(characters)/sizeof(char) - 1; // -1 since characters has a null char
|
||||||
|
char* pointers_to_chars[N]; // at the end.
|
||||||
|
for (int i = 0; i < N; ++i)
|
||||||
|
pointers_to_chars[i] = &characters[i];
|
||||||
|
|
||||||
|
// Example of using indirect_iterator
|
||||||
|
|
||||||
|
boost::indirect_iterator<char**, char>
|
||||||
|
indirect_first(pointers_to_chars), indirect_last(pointers_to_chars + N);
|
||||||
|
|
||||||
|
std::copy(indirect_first, indirect_last, std::ostream_iterator<char>(std::cout, ","));
|
||||||
|
std::cout << std::endl;
|
||||||
|
|
||||||
|
|
||||||
|
// Example of making mutable and constant indirect iterators
|
||||||
|
|
||||||
|
char mutable_characters[N];
|
||||||
|
char* pointers_to_mutable_chars[N];
|
||||||
|
for (int j = 0; j < N; ++j)
|
||||||
|
pointers_to_mutable_chars[j] = &mutable_characters[j];
|
||||||
|
|
||||||
|
boost::indirect_iterator<char* const*> mutable_indirect_first(pointers_to_mutable_chars),
|
||||||
|
mutable_indirect_last(pointers_to_mutable_chars + N);
|
||||||
|
boost::indirect_iterator<char* const*, char const> const_indirect_first(pointers_to_chars),
|
||||||
|
const_indirect_last(pointers_to_chars + N);
|
||||||
|
|
||||||
|
std::transform(const_indirect_first, const_indirect_last,
|
||||||
|
mutable_indirect_first, std::bind1st(std::plus<char>(), 1));
|
||||||
|
|
||||||
|
std::copy(mutable_indirect_first, mutable_indirect_last,
|
||||||
|
std::ostream_iterator<char>(std::cout, ","));
|
||||||
|
std::cout << std::endl;
|
||||||
|
|
||||||
|
|
||||||
|
// Example of using make_indirect_iterator()
|
||||||
|
|
||||||
|
std::copy(boost::make_indirect_iterator(pointers_to_chars),
|
||||||
|
boost::make_indirect_iterator(pointers_to_chars + N),
|
||||||
|
std::ostream_iterator<char>(std::cout, ","));
|
||||||
|
std::cout << std::endl;
|
||||||
|
|
||||||
|
|
||||||
|
The output is::
|
||||||
|
|
||||||
|
a,b,c,d,e,f,g,
|
||||||
|
b,c,d,e,f,g,h,
|
||||||
|
a,b,c,d,e,f,g,
|
||||||
|
|
||||||
|
|
||||||
|
The source code for this example can be found `here`__.
|
||||||
|
|
||||||
|
__ ../example/indirect_iterator_example.cpp
|
||||||
|
|
181
doc/indirect_iterator_ref.rst
Normal file
181
doc/indirect_iterator_ref.rst
Normal file
@ -0,0 +1,181 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <
|
||||||
|
class Iterator
|
||||||
|
, class Value = use_default
|
||||||
|
, class CategoryOrTraversal = use_default
|
||||||
|
, class Reference = use_default
|
||||||
|
, class Difference = use_default
|
||||||
|
>
|
||||||
|
class indirect_iterator
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
typedef /* see below */ value_type;
|
||||||
|
typedef /* see below */ reference;
|
||||||
|
typedef /* see below */ pointer;
|
||||||
|
typedef /* see below */ difference_type;
|
||||||
|
typedef /* see below */ iterator_category;
|
||||||
|
|
||||||
|
indirect_iterator();
|
||||||
|
indirect_iterator(Iterator x);
|
||||||
|
|
||||||
|
template <
|
||||||
|
class Iterator2, class Value2, class Category2
|
||||||
|
, class Reference2, class Difference2
|
||||||
|
>
|
||||||
|
indirect_iterator(
|
||||||
|
indirect_iterator<
|
||||||
|
Iterator2, Value2, Category2, Reference2, Difference2
|
||||||
|
> const& y
|
||||||
|
, typename enable_if_convertible<Iterator2, Iterator>::type* = 0 // exposition
|
||||||
|
);
|
||||||
|
|
||||||
|
Iterator const& base() const;
|
||||||
|
reference operator*() const;
|
||||||
|
indirect_iterator& operator++();
|
||||||
|
indirect_iterator& operator--();
|
||||||
|
private:
|
||||||
|
Iterator m_iterator; // exposition
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
The member types of ``indirect_iterator`` are defined according to
|
||||||
|
the following pseudo-code, where ``V`` is
|
||||||
|
``iterator_traits<Iterator>::value_type``
|
||||||
|
|
||||||
|
.. parsed-literal::
|
||||||
|
|
||||||
|
if (Value is use_default) then
|
||||||
|
typedef remove_const<pointee<V>::type>::type value_type;
|
||||||
|
else
|
||||||
|
typedef remove_const<Value>::type value_type;
|
||||||
|
|
||||||
|
if (Reference is use_default) then
|
||||||
|
if (Value is use_default) then
|
||||||
|
typedef indirect_reference<V>::type reference;
|
||||||
|
else
|
||||||
|
typedef Value& reference;
|
||||||
|
else
|
||||||
|
typedef Reference reference;
|
||||||
|
|
||||||
|
if (Value is use_default) then
|
||||||
|
typedef pointee<V>::type\* pointer;
|
||||||
|
else
|
||||||
|
typedef Value\* pointer;
|
||||||
|
|
||||||
|
if (Difference is use_default)
|
||||||
|
typedef iterator_traits<Iterator>::difference_type difference_type;
|
||||||
|
else
|
||||||
|
typedef Difference difference_type;
|
||||||
|
|
||||||
|
if (CategoryOrTraversal is use_default)
|
||||||
|
typedef *iterator-category* (
|
||||||
|
iterator_traversal<Iterator>::type,``reference``,``value_type``
|
||||||
|
) iterator_category;
|
||||||
|
else
|
||||||
|
typedef *iterator-category* (
|
||||||
|
CategoryOrTraversal,``reference``,``value_type``
|
||||||
|
) iterator_category;
|
||||||
|
|
||||||
|
|
||||||
|
``indirect_iterator`` requirements
|
||||||
|
..................................
|
||||||
|
|
||||||
|
The expression ``*v``, where ``v`` is an object of
|
||||||
|
``iterator_traits<Iterator>::value_type``, shall be valid
|
||||||
|
expression and convertible to ``reference``. ``Iterator`` shall
|
||||||
|
model the traversal concept indicated by ``iterator_category``.
|
||||||
|
``Value``, ``Reference``, and ``Difference`` shall be chosen so
|
||||||
|
that ``value_type``, ``reference``, and ``difference_type`` meet
|
||||||
|
the requirements indicated by ``iterator_category``.
|
||||||
|
|
||||||
|
[Note: there are further requirements on the
|
||||||
|
``iterator_traits<Iterator>::value_type`` if the ``Value``
|
||||||
|
parameter is not ``use_default``, as implied by the algorithm for
|
||||||
|
deducing the default for the ``value_type`` member.]
|
||||||
|
|
||||||
|
``indirect_iterator`` models
|
||||||
|
............................
|
||||||
|
|
||||||
|
In addition to the concepts indicated by ``iterator_category``
|
||||||
|
and by ``iterator_traversal<indirect_iterator>::type``, a
|
||||||
|
specialization of ``indirect_iterator`` models the following
|
||||||
|
concepts, Where ``v`` is an object of
|
||||||
|
``iterator_traits<Iterator>::value_type``:
|
||||||
|
|
||||||
|
* Readable Iterator if ``reference(*v)`` is convertible to
|
||||||
|
``value_type``.
|
||||||
|
|
||||||
|
* Writable Iterator if ``reference(*v) = t`` is a valid
|
||||||
|
expression (where ``t`` is an object of type
|
||||||
|
``indirect_iterator::value_type``)
|
||||||
|
|
||||||
|
* Lvalue Iterator if ``reference`` is a reference type.
|
||||||
|
|
||||||
|
``indirect_iterator<X,V1,C1,R1,D1>`` is interoperable with
|
||||||
|
``indirect_iterator<Y,V2,C2,R2,D2>`` if and only if ``X`` is
|
||||||
|
interoperable with ``Y``.
|
||||||
|
|
||||||
|
|
||||||
|
``indirect_iterator`` operations
|
||||||
|
................................
|
||||||
|
|
||||||
|
In addition to the operations required by the concepts described
|
||||||
|
above, specializations of ``indirect_iterator`` provide the
|
||||||
|
following operations.
|
||||||
|
|
||||||
|
|
||||||
|
``indirect_iterator();``
|
||||||
|
|
||||||
|
:Requires: ``Iterator`` must be Default Constructible.
|
||||||
|
:Effects: Constructs an instance of ``indirect_iterator`` with
|
||||||
|
a default-constructed ``m_iterator``.
|
||||||
|
|
||||||
|
|
||||||
|
``indirect_iterator(Iterator x);``
|
||||||
|
|
||||||
|
:Effects: Constructs an instance of ``indirect_iterator`` with
|
||||||
|
``m_iterator`` copy constructed from ``x``.
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <
|
||||||
|
class Iterator2, class Value2, unsigned Access, class Traversal
|
||||||
|
, class Reference2, class Difference2
|
||||||
|
>
|
||||||
|
indirect_iterator(
|
||||||
|
indirect_iterator<
|
||||||
|
Iterator2, Value2, Access, Traversal, Reference2, Difference2
|
||||||
|
> const& y
|
||||||
|
, typename enable_if_convertible<Iterator2, Iterator>::type* = 0 // exposition
|
||||||
|
);
|
||||||
|
|
||||||
|
:Requires: ``Iterator2`` is implicitly convertible to ``Iterator``.
|
||||||
|
:Effects: Constructs an instance of ``indirect_iterator`` whose
|
||||||
|
``m_iterator`` subobject is constructed from ``y.base()``.
|
||||||
|
|
||||||
|
|
||||||
|
``Iterator const& base() const;``
|
||||||
|
|
||||||
|
:Returns: ``m_iterator``
|
||||||
|
|
||||||
|
|
||||||
|
``reference operator*() const;``
|
||||||
|
|
||||||
|
:Returns: ``**m_iterator``
|
||||||
|
|
||||||
|
|
||||||
|
``indirect_iterator& operator++();``
|
||||||
|
|
||||||
|
:Effects: ``++m_iterator``
|
||||||
|
:Returns: ``*this``
|
||||||
|
|
||||||
|
|
||||||
|
``indirect_iterator& operator--();``
|
||||||
|
|
||||||
|
:Effects: ``--m_iterator``
|
||||||
|
:Returns: ``*this``
|
29
doc/indirect_reference_ref.rst
Normal file
29
doc/indirect_reference_ref.rst
Normal file
@ -0,0 +1,29 @@
|
|||||||
|
.. Copyright David Abrahams 2004. Use, modification and distribution is
|
||||||
|
.. subject to the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <class Dereferenceable>
|
||||||
|
struct indirect_reference
|
||||||
|
{
|
||||||
|
typedef /* see below */ type;
|
||||||
|
};
|
||||||
|
|
||||||
|
:Requires: For an object ``x`` of type ``Dereferenceable``, ``*x``
|
||||||
|
is well-formed. If ``++x`` is ill-formed it shall neither be
|
||||||
|
ambiguous nor shall it violate access control, and
|
||||||
|
``pointee<Dereferenceable>::type&`` shall be well-formed.
|
||||||
|
Otherwise ``iterator_traits<Dereferenceable>::reference`` shall
|
||||||
|
be well formed. [Note: These requirements need not apply to
|
||||||
|
explicit or partial specializations of ``indirect_reference``]
|
||||||
|
|
||||||
|
``type`` is determined according to the following algorithm, where
|
||||||
|
``x`` is an object of type ``Dereferenceable``::
|
||||||
|
|
||||||
|
if ( ++x is ill-formed )
|
||||||
|
return ``pointee<Dereferenceable>::type&``
|
||||||
|
else
|
||||||
|
std::iterator_traits<Dereferenceable>::reference
|
||||||
|
|
||||||
|
|
238
doc/interoperability-revisited.rst
Normal file
238
doc/interoperability-revisited.rst
Normal file
@ -0,0 +1,238 @@
|
|||||||
|
++++++++++++++++++++++++++++
|
||||||
|
Interoperability Revisited
|
||||||
|
++++++++++++++++++++++++++++
|
||||||
|
|
||||||
|
:date: $Date$
|
||||||
|
:copyright: Copyright Thomas Witt 2004.
|
||||||
|
|
||||||
|
.. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
Problem
|
||||||
|
=======
|
||||||
|
|
||||||
|
The current iterator_facade specification makes it unneccessarily tedious to
|
||||||
|
implement interoperable iterators.
|
||||||
|
|
||||||
|
In the following text a simplified example of the current iterator_facade specification is used to
|
||||||
|
illustrate the problem.
|
||||||
|
|
||||||
|
In the current specification binary operators are implemented in the following way::
|
||||||
|
|
||||||
|
template <class Derived>
|
||||||
|
struct Facade
|
||||||
|
{
|
||||||
|
};
|
||||||
|
|
||||||
|
template <class T1, T2>
|
||||||
|
struct is_interoperable :
|
||||||
|
or_<
|
||||||
|
is_convertible<T1, T2>
|
||||||
|
, is_convertible<T2, T1>
|
||||||
|
>
|
||||||
|
{};
|
||||||
|
|
||||||
|
template<
|
||||||
|
class Derived1
|
||||||
|
, class Derived2
|
||||||
|
>
|
||||||
|
enable_if<is_interoperable<Derived1, Derived2>, bool> operator==(
|
||||||
|
Derived1 const& lhs
|
||||||
|
, Derived2 const& rhs
|
||||||
|
)
|
||||||
|
{
|
||||||
|
return static_cast<Derived1 const&>(lhs).equal_to(static_cast<Derived2 const&(rhs));
|
||||||
|
}
|
||||||
|
|
||||||
|
The problem with this is that operator== always forwards to Derived1::equal_to. The net effect is that the
|
||||||
|
following "obvious" implementation of to interoperable types does
|
||||||
|
not quite work. ::
|
||||||
|
|
||||||
|
struct Mutable : Facade<Mutable>
|
||||||
|
{
|
||||||
|
bool equal_to(Mutable const&);
|
||||||
|
};
|
||||||
|
|
||||||
|
struct Constant : Facade<Constant>
|
||||||
|
{
|
||||||
|
Constant();
|
||||||
|
Constant(Constant const&);
|
||||||
|
Constant(Mutable const&);
|
||||||
|
|
||||||
|
...
|
||||||
|
|
||||||
|
bool equal_to(Constant const&);
|
||||||
|
};
|
||||||
|
|
||||||
|
Constant c;
|
||||||
|
Mutable m;
|
||||||
|
|
||||||
|
c == m; // ok, dispatched to Constant::equal_to
|
||||||
|
m == c; // !! error, dispatched to Mutable::equal_to
|
||||||
|
|
||||||
|
Instead the following "slightly" more complicated implementation is necessary
|
||||||
|
|
||||||
|
struct Mutable : Facade<Mutable>
|
||||||
|
{
|
||||||
|
template <class T>
|
||||||
|
enable_if<is_convertible<Mutable, T> || is_convertible<T, Mutable>, bool>::type equal_to(T const&);
|
||||||
|
};
|
||||||
|
|
||||||
|
struct Constant : Tag<Constant>
|
||||||
|
{
|
||||||
|
Constant();
|
||||||
|
Constant(Constant const&);
|
||||||
|
Constant(Mutable const&);
|
||||||
|
|
||||||
|
template <class T>
|
||||||
|
enable_if<is_convertible<Constant, T> || is_convertible<T, Constant>, bool>::type equal_to(T const&);
|
||||||
|
};
|
||||||
|
|
||||||
|
Beside the fact that the code is significantly more complex to understand and to teach there is
|
||||||
|
a major design problem lurking here. Note that in both types equal_to is a function template with
|
||||||
|
an unconstrained argument T. This is necessary so that further types can be made interoperable with
|
||||||
|
Mutable or Constant. Would Mutable be defined as ::
|
||||||
|
|
||||||
|
struct Mutable : Facade<Mutable>
|
||||||
|
{
|
||||||
|
bool equal_to(Mutable const&);
|
||||||
|
bool equal_to(Constant const&);
|
||||||
|
};
|
||||||
|
|
||||||
|
Constant and Mutable would still be interoperable but no further interoperable could be added
|
||||||
|
without changing Mutable. Even if this would be considered acceptable the current specification forces
|
||||||
|
a two way dependency between interoperable types. Note in the templated equal_to case this dependency
|
||||||
|
is implicitly created when specializing equal_to.
|
||||||
|
|
||||||
|
Solution
|
||||||
|
========
|
||||||
|
|
||||||
|
The two way dependency can be avoided by enabling type conversion in the binary operator
|
||||||
|
implementation. Note that this is the usual way interoperability betwween types is achieved
|
||||||
|
for binary operators and one reason why binary operators are usually implemented as non-members.
|
||||||
|
|
||||||
|
A simple implementation of this strategy would look like this ::
|
||||||
|
|
||||||
|
template<
|
||||||
|
class T1
|
||||||
|
, class T2
|
||||||
|
>
|
||||||
|
struct interoperable_base :
|
||||||
|
if_<
|
||||||
|
is_convertible<
|
||||||
|
T2
|
||||||
|
, T1
|
||||||
|
>
|
||||||
|
, T1
|
||||||
|
, T2>
|
||||||
|
{};
|
||||||
|
|
||||||
|
|
||||||
|
template<
|
||||||
|
class Derived1
|
||||||
|
, class Derived2
|
||||||
|
>
|
||||||
|
enable_if<is_interoperable<Derived1, Derived2>, bool> operator==(
|
||||||
|
Derived1 const& lhs
|
||||||
|
, Derived2 const& rhs
|
||||||
|
)
|
||||||
|
{
|
||||||
|
typedef interoperable_base<
|
||||||
|
Derived1
|
||||||
|
, Derived2
|
||||||
|
>::type Base;
|
||||||
|
|
||||||
|
return static_cast<Base const&>(lhs).equal_to(static_cast<Derived2 const&(rhs));
|
||||||
|
}
|
||||||
|
|
||||||
|
This way our original simple and "obvious" implementation would
|
||||||
|
work again. ::
|
||||||
|
|
||||||
|
c == m; // ok, dispatched to Constant::equal_to
|
||||||
|
m == c; // ok, dispatched to Constant::equal_to, m converted to Constant
|
||||||
|
|
||||||
|
The backdraw of this approach is that a possibly costly conversion of iterator objects
|
||||||
|
is forced on the user even in cases where direct comparison could be implemented
|
||||||
|
in a much more efficient way. This problem arises especially for iterator_adaptor
|
||||||
|
specializations and can be significantly slow down the iteration over ranges. Given the fact
|
||||||
|
that iteration is a very basic operation this possible performance degradation is not
|
||||||
|
acceptable.
|
||||||
|
|
||||||
|
Luckily whe can have our cake and eat it by a slightly more clever implementation of the binary
|
||||||
|
operators. ::
|
||||||
|
|
||||||
|
template<
|
||||||
|
class Derived1
|
||||||
|
, class Derived2
|
||||||
|
>
|
||||||
|
enable_if<is_convertible<Derived2, Derived1>, bool> operator==(
|
||||||
|
Derived1 const& lhs
|
||||||
|
, Derived2 const& rhs
|
||||||
|
)
|
||||||
|
{
|
||||||
|
return static_cast<Derived1 const&>(lhs).equal_to(static_cast<Derived2 const&(rhs));
|
||||||
|
}
|
||||||
|
|
||||||
|
template<
|
||||||
|
class Derived1
|
||||||
|
, class Derived2
|
||||||
|
>
|
||||||
|
enable_if<is_convertible<Derived1, Derived2>, bool> operator==(
|
||||||
|
Derived1 const& lhs
|
||||||
|
, Derived2 const& rhs
|
||||||
|
)
|
||||||
|
{
|
||||||
|
return static_cast<Derived2 const&>(rhs).equal_to(static_cast<Derived1 const&(lhs));
|
||||||
|
}
|
||||||
|
|
||||||
|
Given our simple and obvious definition of Mutable and Constant nothing has changed yet. ::
|
||||||
|
|
||||||
|
c == m; // ok, dispatched to Constant::equal_to, m converted to Constant
|
||||||
|
m == c; // ok, dispatched to Constant::equal_to, m converted to Constant
|
||||||
|
|
||||||
|
But now the user can avoid the type conversion by supplying the
|
||||||
|
appropriate overload in Constant ::
|
||||||
|
|
||||||
|
struct Constant : Facade<Constant>
|
||||||
|
{
|
||||||
|
Constant();
|
||||||
|
Constant(Constant const&);
|
||||||
|
Constant(Mutable const&);
|
||||||
|
|
||||||
|
...
|
||||||
|
|
||||||
|
bool equal_to(Constant const&);
|
||||||
|
bool equal_to(Mutable const&);
|
||||||
|
};
|
||||||
|
|
||||||
|
c == m; // ok, dispatched to Constant::equal_to(Mutable const&), no conversion
|
||||||
|
m == c; // ok, dispatched to Constant::equal_to(Mutable const&), no conversion
|
||||||
|
|
||||||
|
This definition of operator== introduces a possible ambiguity when both types are convertible
|
||||||
|
to each other. I don't think this is a problem as this behaviour is the same with concrete types.
|
||||||
|
I.e. ::
|
||||||
|
|
||||||
|
struct A {};
|
||||||
|
|
||||||
|
bool operator==(A, A);
|
||||||
|
|
||||||
|
struct B { B(A); };
|
||||||
|
|
||||||
|
bool operator==(B, B);
|
||||||
|
|
||||||
|
A a;
|
||||||
|
B b(a);
|
||||||
|
|
||||||
|
a == b; // error, ambiguous overload
|
||||||
|
|
||||||
|
Effect
|
||||||
|
======
|
||||||
|
|
||||||
|
Iterator implementations using iterator_facade look exactly as if they were
|
||||||
|
"hand-implemented" (I am working on better wording).
|
||||||
|
|
||||||
|
a) Less burden for the user
|
||||||
|
|
||||||
|
b) The definition (standardese) of specialized adpters might be easier
|
||||||
|
(This has to be proved yet)
|
152
doc/issues.rst
Normal file
152
doc/issues.rst
Normal file
@ -0,0 +1,152 @@
|
|||||||
|
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
|
||||||
|
Problem with ``is_writable`` and ``is_swappable`` in N1550_
|
||||||
|
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
|
||||||
|
|
||||||
|
.. _N1550: http://www.boost-consulting.com/writing/n1550.html
|
||||||
|
.. _N1530: http://anubis.dkuug.dk/jtc1/sc22/wg21/docs/papers/2003/n1530.html
|
||||||
|
|
||||||
|
:Author: David Abrahams and Jeremy Siek
|
||||||
|
:Contact: dave@boost-consulting.com, jsiek@osl.iu.edu
|
||||||
|
:Organization: `Boost Consulting`_, Indiana University Bloomington
|
||||||
|
:date: $Date$
|
||||||
|
:Copyright: Copyright David Abrahams, Jeremy Siek 2003. Use, modification and
|
||||||
|
distribution is subject to the Boost Software License,
|
||||||
|
Version 1.0. (See accompanying file LICENSE_1_0.txt or copy
|
||||||
|
at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
.. _`Boost Consulting`: http://www.boost-consulting.com
|
||||||
|
|
||||||
|
.. contents:: Table of Contents
|
||||||
|
|
||||||
|
==============
|
||||||
|
Introduction
|
||||||
|
==============
|
||||||
|
|
||||||
|
The ``is_writable`` and ``is_swappable`` traits classes in N1550_
|
||||||
|
provide a mechanism for determining at compile time if an iterator
|
||||||
|
type is a model of the new Writable Iterator and Swappable Iterator
|
||||||
|
concepts, analogous to ``iterator_traits<X>::iterator_category``
|
||||||
|
for the old iterator concepts. For backward compatibility,
|
||||||
|
``is_writable`` and ``is_swappable`` not only work with new
|
||||||
|
iterators, but they also are intended to work for old
|
||||||
|
iterators (iterators that meet the requirements for one of the
|
||||||
|
iterator concepts in the current standard). In the case of old
|
||||||
|
iterators, the writability and swapability is deduced based on the
|
||||||
|
``iterator_category`` and also the ``reference`` type. The
|
||||||
|
specification for this deduction gives false positives for forward
|
||||||
|
iterators that have non-assignable value types.
|
||||||
|
|
||||||
|
To review, the part of the ``is_writable`` trait definition which
|
||||||
|
applies to old iterators is::
|
||||||
|
|
||||||
|
if (cat is convertible to output_iterator_tag)
|
||||||
|
return true;
|
||||||
|
else if (cat is convertible to forward_iterator_tag
|
||||||
|
and iterator_traits<Iterator>::reference is a
|
||||||
|
mutable reference)
|
||||||
|
return true;
|
||||||
|
else
|
||||||
|
return false;
|
||||||
|
|
||||||
|
Suppose the ``value_type`` of the iterator ``It`` has a private
|
||||||
|
assignment operator::
|
||||||
|
|
||||||
|
class B {
|
||||||
|
public:
|
||||||
|
...
|
||||||
|
private:
|
||||||
|
B& operator=(const B&);
|
||||||
|
};
|
||||||
|
|
||||||
|
and suppose the ``reference`` type of the iterator is ``B&``. In
|
||||||
|
that case, ``is_writable<It>::value`` will be true when in fact
|
||||||
|
attempting to write into ``B`` will cause an error.
|
||||||
|
|
||||||
|
The same problem applies to ``is_swappable``.
|
||||||
|
|
||||||
|
|
||||||
|
====================
|
||||||
|
Proposed Resolution
|
||||||
|
====================
|
||||||
|
|
||||||
|
1. Remove the ``is_writable`` and ``is_swappable`` traits, and remove the
|
||||||
|
requirements in the Writable Iterator and Swappable Iterator concepts
|
||||||
|
that require their models to support these traits.
|
||||||
|
|
||||||
|
2. Change the ``is_readable`` specification to be:
|
||||||
|
``is_readable<X>::type`` is ``true_type`` if the
|
||||||
|
result type of ``X::operator*`` is convertible to
|
||||||
|
``iterator_traits<X>::value_type`` and is ``false_type``
|
||||||
|
otherwise. Also, ``is_readable`` is required to satisfy
|
||||||
|
the requirements for the UnaryTypeTrait concept
|
||||||
|
(defined in the type traits proposal).
|
||||||
|
|
||||||
|
Remove the requirement for support of the ``is_readable`` trait from
|
||||||
|
the Readable Iterator concept.
|
||||||
|
|
||||||
|
|
||||||
|
3. Remove the ``iterator_tag`` class.
|
||||||
|
|
||||||
|
4. Change the specification of ``traversal_category`` to::
|
||||||
|
|
||||||
|
traversal-category(Iterator) =
|
||||||
|
let cat = iterator_traits<Iterator>::iterator_category
|
||||||
|
if (cat is convertible to incrementable_iterator_tag)
|
||||||
|
return cat; // Iterator is a new iterator
|
||||||
|
else if (cat is convertible to random_access_iterator_tag)
|
||||||
|
return random_access_traversal_tag;
|
||||||
|
else if (cat is convertible to bidirectional_iterator_tag)
|
||||||
|
return bidirectional_traversal_tag;
|
||||||
|
else if (cat is convertible to forward_iterator_tag)
|
||||||
|
return forward_traversal_tag;
|
||||||
|
else if (cat is convertible to input_iterator_tag)
|
||||||
|
return single_pass_iterator_tag;
|
||||||
|
else if (cat is convertible to output_iterator_tag)
|
||||||
|
return incrementable_iterator_tag;
|
||||||
|
else
|
||||||
|
return null_category_tag;
|
||||||
|
|
||||||
|
|
||||||
|
==========
|
||||||
|
Rationale
|
||||||
|
==========
|
||||||
|
|
||||||
|
1. There are two reasons for removing ``is_writable``
|
||||||
|
and ``is_swappable``. The first is that we do not know of
|
||||||
|
a way to fix the specification so that it gives the correct
|
||||||
|
answer for all iterators. Second, there was only a weak
|
||||||
|
motivation for having ``is_writable`` and ``is_swappable``
|
||||||
|
there in the first place. The main motivation was simply
|
||||||
|
uniformity: we have tags for the old iterator categories
|
||||||
|
so we should have tags for the new iterator categories.
|
||||||
|
While having tags and the capability to dispatch based
|
||||||
|
on the traversal categories is often used, we see
|
||||||
|
less of a need for dispatching based on writability
|
||||||
|
and swappability, since typically algorithms
|
||||||
|
that need these capabilities have no alternative if
|
||||||
|
they are not provided.
|
||||||
|
|
||||||
|
2. We discovered that the ``is_readable`` trait can be implemented
|
||||||
|
using only the iterator type itself and its ``value_type``.
|
||||||
|
Therefore we remove the requirement for ``is_readable`` from the
|
||||||
|
Readable Iterator concept, and change the definition of
|
||||||
|
``is_readable`` so that it works for any iterator type.
|
||||||
|
|
||||||
|
3. The purpose of the ``iterator_tag`` class was to
|
||||||
|
bundle the traversal and access category tags
|
||||||
|
into the ``iterator_category`` typedef.
|
||||||
|
With ``is_writable`` and ``is_swappable`` gone, and
|
||||||
|
``is_readable`` no longer in need of special hints,
|
||||||
|
there is no reason for iterators to provide
|
||||||
|
information about the access capabilities of an iterator.
|
||||||
|
Thus there is no need for the ``iterator_tag``. The
|
||||||
|
traversal tag can be directly used for the
|
||||||
|
``iterator_category``. If a new iterator is intended to be backward
|
||||||
|
compatible with old iterator concepts, a tag type
|
||||||
|
that is convertible to both one of the new traversal tags
|
||||||
|
and also to an old iterator tag can be created and use
|
||||||
|
for the ``iterator_category``.
|
||||||
|
|
||||||
|
4. The changes to the specification of ``traversal_category`` are a
|
||||||
|
direct result of the removal of ``iterator_tag``.
|
||||||
|
|
461
doc/iterator_adaptor.html
Normal file
461
doc/iterator_adaptor.html
Normal file
@ -0,0 +1,461 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" />
|
||||||
|
<title>Iterator Adaptor</title>
|
||||||
|
<meta name="author" content="David Abrahams, Jeremy Siek, Thomas Witt" />
|
||||||
|
<meta name="organization" content="Boost Consulting, Indiana University Open Systems Lab, University of Hanover Institute for Transport Railway Operation and Construction" />
|
||||||
|
<meta name="date" content="2006-09-11" />
|
||||||
|
<meta name="copyright" content="Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003." />
|
||||||
|
<link rel="stylesheet" href="../../../rst.css" type="text/css" />
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="iterator-adaptor">
|
||||||
|
<h1 class="title">Iterator Adaptor</h1>
|
||||||
|
<table class="docinfo" frame="void" rules="none">
|
||||||
|
<col class="docinfo-name" />
|
||||||
|
<col class="docinfo-content" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><th class="docinfo-name">Author:</th>
|
||||||
|
<td>David Abrahams, Jeremy Siek, Thomas Witt</td></tr>
|
||||||
|
<tr><th class="docinfo-name">Contact:</th>
|
||||||
|
<td><a class="first reference external" href="mailto:dave@boost-consulting.com">dave@boost-consulting.com</a>, <a class="reference external" href="mailto:jsiek@osl.iu.edu">jsiek@osl.iu.edu</a>, <a class="last reference external" href="mailto:witt@ive.uni-hannover.de">witt@ive.uni-hannover.de</a></td></tr>
|
||||||
|
<tr><th class="docinfo-name">Organization:</th>
|
||||||
|
<td><a class="first reference external" href="http://www.boost-consulting.com">Boost Consulting</a>, Indiana University <a class="reference external" href="http://www.osl.iu.edu">Open Systems
|
||||||
|
Lab</a>, University of Hanover <a class="last reference external" href="http://www.ive.uni-hannover.de">Institute for Transport
|
||||||
|
Railway Operation and Construction</a></td></tr>
|
||||||
|
<tr><th class="docinfo-name">Date:</th>
|
||||||
|
<td>2006-09-11</td></tr>
|
||||||
|
<tr><th class="docinfo-name">Copyright:</th>
|
||||||
|
<td>Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003.</td></tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<!-- Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">abstract:</th><td class="field-body"></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<!-- Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<!-- Version 1.1 of this ReStructuredText document corresponds to
|
||||||
|
n1530_, the paper accepted by the LWG. -->
|
||||||
|
<!-- Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003. -->
|
||||||
|
<p>Each specialization of the <tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> class template is derived from
|
||||||
|
a specialization of <tt class="docutils literal"><span class="pre">iterator_facade</span></tt>. The core interface functions
|
||||||
|
expected by <tt class="docutils literal"><span class="pre">iterator_facade</span></tt> are implemented in terms of the
|
||||||
|
<tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt>'s <tt class="docutils literal"><span class="pre">Base</span></tt> template parameter. A class derived
|
||||||
|
from <tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> typically redefines some of the core
|
||||||
|
interface functions to adapt the behavior of the <tt class="docutils literal"><span class="pre">Base</span></tt> type.
|
||||||
|
Whether the derived class models any of the standard iterator concepts
|
||||||
|
depends on the operations supported by the <tt class="docutils literal"><span class="pre">Base</span></tt> type and which
|
||||||
|
core interface functions of <tt class="docutils literal"><span class="pre">iterator_facade</span></tt> are redefined in the
|
||||||
|
<tt class="docutils literal"><span class="pre">Derived</span></tt> class.</p>
|
||||||
|
<div class="contents topic" id="table-of-contents">
|
||||||
|
<p class="topic-title first">Table of Contents</p>
|
||||||
|
<ul class="simple">
|
||||||
|
<li><a class="reference internal" href="#overview" id="id6">Overview</a></li>
|
||||||
|
<li><a class="reference internal" href="#reference" id="id7">Reference</a><ul>
|
||||||
|
<li><a class="reference internal" href="#iterator-adaptor-requirements" id="id8"><tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> requirements</a></li>
|
||||||
|
<li><a class="reference internal" href="#iterator-adaptor-base-class-parameters" id="id9"><tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> base class parameters</a></li>
|
||||||
|
<li><a class="reference internal" href="#iterator-adaptor-public-operations" id="id10"><tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> public operations</a></li>
|
||||||
|
<li><a class="reference internal" href="#iterator-adaptor-protected-member-functions" id="id11"><tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> protected member functions</a></li>
|
||||||
|
<li><a class="reference internal" href="#iterator-adaptor-private-member-functions" id="id12"><tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> private member functions</a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#tutorial-example" id="id13">Tutorial Example</a></li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="overview">
|
||||||
|
<h1><a class="toc-backref" href="#id6">Overview</a></h1>
|
||||||
|
<!-- Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<!-- Version 1.2 of this ReStructuredText document corresponds to
|
||||||
|
n1530_, the paper accepted by the LWG for TR1. -->
|
||||||
|
<!-- Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003. -->
|
||||||
|
<p>The <tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> class template adapts some <tt class="docutils literal"><span class="pre">Base</span></tt><a class="footnote-reference" href="#base" id="id1"><sup>1</sup></a>
|
||||||
|
type to create a new iterator. Instantiations of <tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt>
|
||||||
|
are derived from a corresponding instantiation of <tt class="docutils literal"><span class="pre">iterator_facade</span></tt>
|
||||||
|
and implement the core behaviors in terms of the <tt class="docutils literal"><span class="pre">Base</span></tt> type. In
|
||||||
|
essence, <tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> merely forwards all operations to an
|
||||||
|
instance of the <tt class="docutils literal"><span class="pre">Base</span></tt> type, which it stores as a member.</p>
|
||||||
|
<table class="docutils footnote" frame="void" id="base" rules="none">
|
||||||
|
<colgroup><col class="label" /><col /></colgroup>
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><td class="label">[1]</td><td><em>(<a class="fn-backref" href="#id1">1</a>, <a class="fn-backref" href="#id3">2</a>)</em> The term "Base" here does not refer to a base class and is
|
||||||
|
not meant to imply the use of derivation. We have followed the lead
|
||||||
|
of the standard library, which provides a base() function to access
|
||||||
|
the underlying iterator object of a <tt class="docutils literal"><span class="pre">reverse_iterator</span></tt> adaptor.</td></tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p>The user of <tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> creates a class derived from an
|
||||||
|
instantiation of <tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> and then selectively
|
||||||
|
redefines some of the core member functions described in the
|
||||||
|
<tt class="docutils literal"><span class="pre">iterator_facade</span></tt> core requirements table. The <tt class="docutils literal"><span class="pre">Base</span></tt> type need
|
||||||
|
not meet the full requirements for an iterator; it need only
|
||||||
|
support the operations used by the core interface functions of
|
||||||
|
<tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> that have not been redefined in the user's
|
||||||
|
derived class.</p>
|
||||||
|
<p>Several of the template parameters of <tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> default
|
||||||
|
to <tt class="docutils literal"><span class="pre">use_default</span></tt>. This allows the
|
||||||
|
user to make use of a default parameter even when she wants to
|
||||||
|
specify a parameter later in the parameter list. Also, the
|
||||||
|
defaults for the corresponding associated types are somewhat
|
||||||
|
complicated, so metaprogramming is required to compute them, and
|
||||||
|
<tt class="docutils literal"><span class="pre">use_default</span></tt> can help to simplify the implementation. Finally,
|
||||||
|
the identity of the <tt class="docutils literal"><span class="pre">use_default</span></tt> type is not left unspecified
|
||||||
|
because specification helps to highlight that the <tt class="docutils literal"><span class="pre">Reference</span></tt>
|
||||||
|
template parameter may not always be identical to the iterator's
|
||||||
|
<tt class="docutils literal"><span class="pre">reference</span></tt> type, and will keep users from making mistakes based on
|
||||||
|
that assumption.</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="reference">
|
||||||
|
<h1><a class="toc-backref" href="#id7">Reference</a></h1>
|
||||||
|
<!-- Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<!-- Version 1.4 of this ReStructuredText document corresponds to
|
||||||
|
n1530_, the paper accepted by the LWG for TR1. -->
|
||||||
|
<!-- Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003. -->
|
||||||
|
<pre class="literal-block">
|
||||||
|
template <
|
||||||
|
class Derived
|
||||||
|
, class Base
|
||||||
|
, class Value = use_default
|
||||||
|
, class CategoryOrTraversal = use_default
|
||||||
|
, class Reference = use_default
|
||||||
|
, class Difference = use_default
|
||||||
|
>
|
||||||
|
class iterator_adaptor
|
||||||
|
: public iterator_facade<Derived, <em>V'</em>, <em>C'</em>, <em>R'</em>, <em>D'</em>> // see <a class="reference internal" href="#base-parameters">details</a>
|
||||||
|
{
|
||||||
|
friend class iterator_core_access;
|
||||||
|
public:
|
||||||
|
iterator_adaptor();
|
||||||
|
explicit iterator_adaptor(Base const& iter);
|
||||||
|
typedef Base base_type;
|
||||||
|
Base const& base() const;
|
||||||
|
protected:
|
||||||
|
typedef iterator_adaptor iterator_adaptor_;
|
||||||
|
Base const& base_reference() const;
|
||||||
|
Base& base_reference();
|
||||||
|
private: // Core iterator interface for iterator_facade.
|
||||||
|
typename iterator_adaptor::reference dereference() const;
|
||||||
|
|
||||||
|
template <
|
||||||
|
class OtherDerived, class OtherIterator, class V, class C, class R, class D
|
||||||
|
>
|
||||||
|
bool equal(iterator_adaptor<OtherDerived, OtherIterator, V, C, R, D> const& x) const;
|
||||||
|
|
||||||
|
void advance(typename iterator_adaptor::difference_type n);
|
||||||
|
void increment();
|
||||||
|
void decrement();
|
||||||
|
|
||||||
|
template <
|
||||||
|
class OtherDerived, class OtherIterator, class V, class C, class R, class D
|
||||||
|
>
|
||||||
|
typename iterator_adaptor::difference_type distance_to(
|
||||||
|
iterator_adaptor<OtherDerived, OtherIterator, V, C, R, D> const& y) const;
|
||||||
|
|
||||||
|
private:
|
||||||
|
Base m_iterator; // exposition only
|
||||||
|
};
|
||||||
|
</pre>
|
||||||
|
<div class="section" id="iterator-adaptor-requirements">
|
||||||
|
<span id="requirements"></span><h2><a class="toc-backref" href="#id8"><tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> requirements</a></h2>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">static_cast<Derived*>(iterator_adaptor*)</span></tt> shall be well-formed.
|
||||||
|
The <tt class="docutils literal"><span class="pre">Base</span></tt> argument shall be Assignable and Copy Constructible.</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="iterator-adaptor-base-class-parameters">
|
||||||
|
<span id="base-parameters"></span><h2><a class="toc-backref" href="#id9"><tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> base class parameters</a></h2>
|
||||||
|
<p>The <em>V'</em>, <em>C'</em>, <em>R'</em>, and <em>D'</em> parameters of the <tt class="docutils literal"><span class="pre">iterator_facade</span></tt>
|
||||||
|
used as a base class in the summary of <tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt>
|
||||||
|
above are defined as follows:</p>
|
||||||
|
<pre class="literal-block">
|
||||||
|
<em>V'</em> = if (Value is use_default)
|
||||||
|
return iterator_traits<Base>::value_type
|
||||||
|
else
|
||||||
|
return Value
|
||||||
|
|
||||||
|
<em>C'</em> = if (CategoryOrTraversal is use_default)
|
||||||
|
return iterator_traversal<Base>::type
|
||||||
|
else
|
||||||
|
return CategoryOrTraversal
|
||||||
|
|
||||||
|
<em>R'</em> = if (Reference is use_default)
|
||||||
|
if (Value is use_default)
|
||||||
|
return iterator_traits<Base>::reference
|
||||||
|
else
|
||||||
|
return Value&
|
||||||
|
else
|
||||||
|
return Reference
|
||||||
|
|
||||||
|
<em>D'</em> = if (Difference is use_default)
|
||||||
|
return iterator_traits<Base>::difference_type
|
||||||
|
else
|
||||||
|
return Difference
|
||||||
|
</pre>
|
||||||
|
<!-- ``iterator_adaptor`` models
|
||||||
|
- - - - - - - - - - - - - - - - - - - - - - - - - - -
|
||||||
|
|
||||||
|
In order for ``Derived`` to model the iterator concepts corresponding
|
||||||
|
to ``iterator_traits<Derived>::iterator_category``, the expressions
|
||||||
|
involving ``m_iterator`` in the specifications of those private member
|
||||||
|
functions of ``iterator_adaptor`` that may be called by
|
||||||
|
``iterator_facade<Derived, V, C, R, D>`` in evaluating any valid
|
||||||
|
expression involving ``Derived`` in those concepts' requirements. -->
|
||||||
|
<!-- The above is confusing and needs a rewrite. -JGS -->
|
||||||
|
<!-- That's why it's removed. We're embracing inheritance, remember? -->
|
||||||
|
</div>
|
||||||
|
<div class="section" id="iterator-adaptor-public-operations">
|
||||||
|
<h2><a class="toc-backref" href="#id10"><tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> public operations</a></h2>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">iterator_adaptor();</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Requires:</th><td class="field-body">The <tt class="docutils literal"><span class="pre">Base</span></tt> type must be Default Constructible.</td>
|
||||||
|
</tr>
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body">An instance of <tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> with
|
||||||
|
<tt class="docutils literal"><span class="pre">m_iterator</span></tt> default constructed.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">explicit</span> <span class="pre">iterator_adaptor(Base</span> <span class="pre">const&</span> <span class="pre">iter);</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body">An instance of <tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> with
|
||||||
|
<tt class="docutils literal"><span class="pre">m_iterator</span></tt> copy constructed from <tt class="docutils literal"><span class="pre">iter</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">Base</span> <span class="pre">const&</span> <span class="pre">base()</span> <span class="pre">const;</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">m_iterator</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="iterator-adaptor-protected-member-functions">
|
||||||
|
<h2><a class="toc-backref" href="#id11"><tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> protected member functions</a></h2>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">Base</span> <span class="pre">const&</span> <span class="pre">base_reference()</span> <span class="pre">const;</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body">A const reference to <tt class="docutils literal"><span class="pre">m_iterator</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">Base&</span> <span class="pre">base_reference();</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body">A non-const reference to <tt class="docutils literal"><span class="pre">m_iterator</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="iterator-adaptor-private-member-functions">
|
||||||
|
<h2><a class="toc-backref" href="#id12"><tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> private member functions</a></h2>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">typename</span> <span class="pre">iterator_adaptor::reference</span> <span class="pre">dereference()</span> <span class="pre">const;</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">*m_iterator</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<pre class="literal-block">
|
||||||
|
template <
|
||||||
|
class OtherDerived, class OtherIterator, class V, class C, class R, class D
|
||||||
|
>
|
||||||
|
bool equal(iterator_adaptor<OtherDerived, OtherIterator, V, C, R, D> const& x) const;
|
||||||
|
</pre>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">m_iterator</span> <span class="pre">==</span> <span class="pre">x.base()</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">void</span> <span class="pre">advance(typename</span> <span class="pre">iterator_adaptor::difference_type</span> <span class="pre">n);</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body"><tt class="docutils literal"><span class="pre">m_iterator</span> <span class="pre">+=</span> <span class="pre">n;</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">void</span> <span class="pre">increment();</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body"><tt class="docutils literal"><span class="pre">++m_iterator;</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">void</span> <span class="pre">decrement();</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body"><tt class="docutils literal"><span class="pre">--m_iterator;</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<pre class="literal-block">
|
||||||
|
template <
|
||||||
|
class OtherDerived, class OtherIterator, class V, class C, class R, class D
|
||||||
|
>
|
||||||
|
typename iterator_adaptor::difference_type distance_to(
|
||||||
|
iterator_adaptor<OtherDerived, OtherIterator, V, C, R, D> const& y) const;
|
||||||
|
</pre>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">y.base()</span> <span class="pre">-</span> <span class="pre">m_iterator</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="tutorial-example">
|
||||||
|
<h1><a class="toc-backref" href="#id13">Tutorial Example</a></h1>
|
||||||
|
<!-- Copyright David Abrahams 2004. Use, modification and distribution is -->
|
||||||
|
<!-- subject to the Boost Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<p>In this section we'll further refine the <tt class="docutils literal"><span class="pre">node_iter</span></tt> class
|
||||||
|
template we developed in the <a class="reference external" href="iterator_facade.html#tutorial-example"><tt class="docutils literal"><span class="pre">iterator_facade</span></tt> tutorial</a>. If you haven't already
|
||||||
|
read that material, you should go back now and check it out because
|
||||||
|
we're going to pick up right where it left off.</p>
|
||||||
|
<div class="sidebar">
|
||||||
|
<p class="first sidebar-title"><tt class="docutils literal"><span class="pre">node_base*</span></tt> really <em>is</em> an iterator</p>
|
||||||
|
<p class="last">It's not really a very interesting iterator, since <tt class="docutils literal"><span class="pre">node_base</span></tt>
|
||||||
|
is an abstract class: a pointer to a <tt class="docutils literal"><span class="pre">node_base</span></tt> just points
|
||||||
|
at some base subobject of an instance of some other class, and
|
||||||
|
incrementing a <tt class="docutils literal"><span class="pre">node_base*</span></tt> moves it past this base subobject
|
||||||
|
to who-knows-where? The most we can do with that incremented
|
||||||
|
position is to compare another <tt class="docutils literal"><span class="pre">node_base*</span></tt> to it. In other
|
||||||
|
words, the original iterator traverses a one-element array.</p>
|
||||||
|
</div>
|
||||||
|
<p>You probably didn't think of it this way, but the <tt class="docutils literal"><span class="pre">node_base*</span></tt>
|
||||||
|
object that underlies <tt class="docutils literal"><span class="pre">node_iterator</span></tt> is itself an iterator,
|
||||||
|
just like all other pointers. If we examine that pointer closely
|
||||||
|
from an iterator perspective, we can see that it has much in common
|
||||||
|
with the <tt class="docutils literal"><span class="pre">node_iterator</span></tt> we're building. First, they share most
|
||||||
|
of the same associated types (<tt class="docutils literal"><span class="pre">value_type</span></tt>, <tt class="docutils literal"><span class="pre">reference</span></tt>,
|
||||||
|
<tt class="docutils literal"><span class="pre">pointer</span></tt>, and <tt class="docutils literal"><span class="pre">difference_type</span></tt>). Second, even some of the
|
||||||
|
core functionality is the same: <tt class="docutils literal"><span class="pre">operator*</span></tt> and <tt class="docutils literal"><span class="pre">operator==</span></tt> on
|
||||||
|
the <tt class="docutils literal"><span class="pre">node_iterator</span></tt> return the result of invoking the same
|
||||||
|
operations on the underlying pointer, via the <tt class="docutils literal"><span class="pre">node_iterator</span></tt>'s
|
||||||
|
<a class="reference external" href="iterator_facade.html#implementing-the-core-operations"><tt class="docutils literal"><span class="pre">dereference</span></tt> and <tt class="docutils literal"><span class="pre">equal</span></tt> member functions</a>). The only real behavioral difference
|
||||||
|
between <tt class="docutils literal"><span class="pre">node_base*</span></tt> and <tt class="docutils literal"><span class="pre">node_iterator</span></tt> can be observed when
|
||||||
|
they are incremented: <tt class="docutils literal"><span class="pre">node_iterator</span></tt> follows the
|
||||||
|
<tt class="docutils literal"><span class="pre">m_next</span></tt> pointer, while <tt class="docutils literal"><span class="pre">node_base*</span></tt> just applies an address offset.</p>
|
||||||
|
<p>It turns out that the pattern of building an iterator on another
|
||||||
|
iterator-like type (the <tt class="docutils literal"><span class="pre">Base</span></tt><a class="footnote-reference" href="#base" id="id3"><sup>1</sup></a> type) while modifying
|
||||||
|
just a few aspects of the underlying type's behavior is an
|
||||||
|
extremely common one, and it's the pattern addressed by
|
||||||
|
<tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt>. Using <tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> is very much like
|
||||||
|
using <tt class="docutils literal"><span class="pre">iterator_facade</span></tt>, but because iterator_adaptor tries to
|
||||||
|
mimic as much of the <tt class="docutils literal"><span class="pre">Base</span></tt> type's behavior as possible, we
|
||||||
|
neither have to supply a <tt class="docutils literal"><span class="pre">Value</span></tt> argument, nor implement any core
|
||||||
|
behaviors other than <tt class="docutils literal"><span class="pre">increment</span></tt>. The implementation of
|
||||||
|
<tt class="docutils literal"><span class="pre">node_iter</span></tt> is thus reduced to:</p>
|
||||||
|
<pre class="literal-block">
|
||||||
|
template <class Value>
|
||||||
|
class node_iter
|
||||||
|
: public boost::iterator_adaptor<
|
||||||
|
node_iter<Value> // Derived
|
||||||
|
, Value* // Base
|
||||||
|
, boost::use_default // Value
|
||||||
|
, boost::forward_traversal_tag // CategoryOrTraversal
|
||||||
|
>
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
struct enabler {}; // a private type avoids misuse
|
||||||
|
|
||||||
|
public:
|
||||||
|
node_iter()
|
||||||
|
: node_iter::iterator_adaptor_(0) {}
|
||||||
|
|
||||||
|
explicit node_iter(Value* p)
|
||||||
|
: node_iter::iterator_adaptor_(p) {}
|
||||||
|
|
||||||
|
template <class OtherValue>
|
||||||
|
node_iter(
|
||||||
|
node_iter<OtherValue> const& other
|
||||||
|
, typename boost::enable_if<
|
||||||
|
boost::is_convertible<OtherValue*,Value*>
|
||||||
|
, enabler
|
||||||
|
>::type = enabler()
|
||||||
|
)
|
||||||
|
: node_iter::iterator_adaptor_(other.base()) {}
|
||||||
|
|
||||||
|
private:
|
||||||
|
friend class boost::iterator_core_access;
|
||||||
|
void increment() { this->base_reference() = this->base()->next(); }
|
||||||
|
};
|
||||||
|
</pre>
|
||||||
|
<p>Note the use of <tt class="docutils literal"><span class="pre">node_iter::iterator_adaptor_</span></tt> here: because
|
||||||
|
<tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> defines a nested <tt class="docutils literal"><span class="pre">iterator_adaptor_</span></tt> type
|
||||||
|
that refers to itself, that gives us a convenient way to refer to
|
||||||
|
the complicated base class type of <tt class="docutils literal"><span class="pre">node_iter<Value></span></tt>. [Note:
|
||||||
|
this technique is known not to work with Borland C++ 5.6.4 and
|
||||||
|
Metrowerks CodeWarrior versions prior to 9.0]</p>
|
||||||
|
<p>You can see an example program that exercises this version of the
|
||||||
|
node iterators <a class="reference external" href="../example/node_iterator3.cpp">here</a>.</p>
|
||||||
|
<p>In the case of <tt class="docutils literal"><span class="pre">node_iter</span></tt>, it's not very compelling to pass
|
||||||
|
<tt class="docutils literal"><span class="pre">boost::use_default</span></tt> as <tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt>'s <tt class="docutils literal"><span class="pre">Value</span></tt>
|
||||||
|
argument; we could have just passed <tt class="docutils literal"><span class="pre">node_iter</span></tt>'s <tt class="docutils literal"><span class="pre">Value</span></tt>
|
||||||
|
along to <tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt>, and that'd even be shorter! Most
|
||||||
|
iterator class templates built with <tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt> are
|
||||||
|
parameterized on another iterator type, rather than on its
|
||||||
|
<tt class="docutils literal"><span class="pre">value_type</span></tt>. For example, <tt class="docutils literal"><span class="pre">boost::reverse_iterator</span></tt> takes an
|
||||||
|
iterator type argument and reverses its direction of traversal,
|
||||||
|
since the original iterator and the reversed one have all the same
|
||||||
|
associated types, <tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt>'s delegation of default
|
||||||
|
types to its <tt class="docutils literal"><span class="pre">Base</span></tt> saves the implementor of
|
||||||
|
<tt class="docutils literal"><span class="pre">boost::reverse_iterator</span></tt> from writing:</p>
|
||||||
|
<pre class="literal-block">
|
||||||
|
std::iterator_traits<Iterator>::<em>some-associated-type</em>
|
||||||
|
</pre>
|
||||||
|
<p>at least four times.</p>
|
||||||
|
<p>We urge you to review the documentation and implementations of
|
||||||
|
<a class="reference external" href="reverse_iterator.html"><tt class="docutils literal"><span class="pre">reverse_iterator</span></tt></a> and the other Boost <a class="reference external" href="index.html#specialized-adaptors">specialized iterator
|
||||||
|
adaptors</a> to get an idea of the sorts of things you can do with
|
||||||
|
<tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt>. In particular, have a look at
|
||||||
|
<a class="reference external" href="transform_iterator.html"><tt class="docutils literal"><span class="pre">transform_iterator</span></tt></a>, which is perhaps the most straightforward
|
||||||
|
adaptor, and also <a class="reference external" href="counting_iterator.html"><tt class="docutils literal"><span class="pre">counting_iterator</span></tt></a>, which demonstrates that
|
||||||
|
<tt class="docutils literal"><span class="pre">iterator_adaptor</span></tt>'s <tt class="docutils literal"><span class="pre">Base</span></tt> type needn't be an iterator.</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<hr class="footer" />
|
||||||
|
<a class="reference external" href="iterator_adaptor.rst">View document source</a>.
|
||||||
|
Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
BIN
doc/iterator_adaptor.pdf
Normal file
BIN
doc/iterator_adaptor.pdf
Normal file
Binary file not shown.
41
doc/iterator_adaptor.rst
Normal file
41
doc/iterator_adaptor.rst
Normal file
@ -0,0 +1,41 @@
|
|||||||
|
.. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
+++++++++++++++++
|
||||||
|
Iterator Adaptor
|
||||||
|
+++++++++++++++++
|
||||||
|
|
||||||
|
:Author: David Abrahams, Jeremy Siek, Thomas Witt
|
||||||
|
:Contact: dave@boost-consulting.com, jsiek@osl.iu.edu, witt@ive.uni-hannover.de
|
||||||
|
:organization: `Boost Consulting`_, Indiana University `Open Systems
|
||||||
|
Lab`_, University of Hanover `Institute for Transport
|
||||||
|
Railway Operation and Construction`_
|
||||||
|
:date: $Date$
|
||||||
|
:copyright: Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003.
|
||||||
|
|
||||||
|
.. _`Boost Consulting`: http://www.boost-consulting.com
|
||||||
|
.. _`Open Systems Lab`: http://www.osl.iu.edu
|
||||||
|
.. _`Institute for Transport Railway Operation and Construction`: http://www.ive.uni-hannover.de
|
||||||
|
|
||||||
|
:abstract:
|
||||||
|
|
||||||
|
.. include:: iterator_adaptor_abstract.rst
|
||||||
|
|
||||||
|
.. contents:: Table of Contents
|
||||||
|
|
||||||
|
Overview
|
||||||
|
========
|
||||||
|
|
||||||
|
.. include:: iterator_adaptor_body.rst
|
||||||
|
|
||||||
|
|
||||||
|
Reference
|
||||||
|
=========
|
||||||
|
|
||||||
|
.. include:: iterator_adaptor_ref.rst
|
||||||
|
|
||||||
|
Tutorial Example
|
||||||
|
================
|
||||||
|
|
||||||
|
.. include:: iterator_adaptor_tutorial.rst
|
19
doc/iterator_adaptor_abstract.rst
Normal file
19
doc/iterator_adaptor_abstract.rst
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
.. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
.. Version 1.1 of this ReStructuredText document corresponds to
|
||||||
|
n1530_, the paper accepted by the LWG.
|
||||||
|
|
||||||
|
.. Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003.
|
||||||
|
|
||||||
|
Each specialization of the ``iterator_adaptor`` class template is derived from
|
||||||
|
a specialization of ``iterator_facade``. The core interface functions
|
||||||
|
expected by ``iterator_facade`` are implemented in terms of the
|
||||||
|
``iterator_adaptor``\ 's ``Base`` template parameter. A class derived
|
||||||
|
from ``iterator_adaptor`` typically redefines some of the core
|
||||||
|
interface functions to adapt the behavior of the ``Base`` type.
|
||||||
|
Whether the derived class models any of the standard iterator concepts
|
||||||
|
depends on the operations supported by the ``Base`` type and which
|
||||||
|
core interface functions of ``iterator_facade`` are redefined in the
|
||||||
|
``Derived`` class.
|
43
doc/iterator_adaptor_body.rst
Normal file
43
doc/iterator_adaptor_body.rst
Normal file
@ -0,0 +1,43 @@
|
|||||||
|
.. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
.. Version 1.2 of this ReStructuredText document corresponds to
|
||||||
|
n1530_, the paper accepted by the LWG for TR1.
|
||||||
|
|
||||||
|
.. Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003.
|
||||||
|
|
||||||
|
The ``iterator_adaptor`` class template adapts some ``Base`` [#base]_
|
||||||
|
type to create a new iterator. Instantiations of ``iterator_adaptor``
|
||||||
|
are derived from a corresponding instantiation of ``iterator_facade``
|
||||||
|
and implement the core behaviors in terms of the ``Base`` type. In
|
||||||
|
essence, ``iterator_adaptor`` merely forwards all operations to an
|
||||||
|
instance of the ``Base`` type, which it stores as a member.
|
||||||
|
|
||||||
|
.. [#base] The term "Base" here does not refer to a base class and is
|
||||||
|
not meant to imply the use of derivation. We have followed the lead
|
||||||
|
of the standard library, which provides a base() function to access
|
||||||
|
the underlying iterator object of a ``reverse_iterator`` adaptor.
|
||||||
|
|
||||||
|
The user of ``iterator_adaptor`` creates a class derived from an
|
||||||
|
instantiation of ``iterator_adaptor`` and then selectively
|
||||||
|
redefines some of the core member functions described in the
|
||||||
|
``iterator_facade`` core requirements table. The ``Base`` type need
|
||||||
|
not meet the full requirements for an iterator; it need only
|
||||||
|
support the operations used by the core interface functions of
|
||||||
|
``iterator_adaptor`` that have not been redefined in the user's
|
||||||
|
derived class.
|
||||||
|
|
||||||
|
Several of the template parameters of ``iterator_adaptor`` default
|
||||||
|
to ``use_default``. This allows the
|
||||||
|
user to make use of a default parameter even when she wants to
|
||||||
|
specify a parameter later in the parameter list. Also, the
|
||||||
|
defaults for the corresponding associated types are somewhat
|
||||||
|
complicated, so metaprogramming is required to compute them, and
|
||||||
|
``use_default`` can help to simplify the implementation. Finally,
|
||||||
|
the identity of the ``use_default`` type is not left unspecified
|
||||||
|
because specification helps to highlight that the ``Reference``
|
||||||
|
template parameter may not always be identical to the iterator's
|
||||||
|
``reference`` type, and will keep users from making mistakes based on
|
||||||
|
that assumption.
|
||||||
|
|
182
doc/iterator_adaptor_ref.rst
Normal file
182
doc/iterator_adaptor_ref.rst
Normal file
@ -0,0 +1,182 @@
|
|||||||
|
.. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
.. Version 1.4 of this ReStructuredText document corresponds to
|
||||||
|
n1530_, the paper accepted by the LWG for TR1.
|
||||||
|
|
||||||
|
.. Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003.
|
||||||
|
|
||||||
|
.. parsed-literal::
|
||||||
|
|
||||||
|
template <
|
||||||
|
class Derived
|
||||||
|
, class Base
|
||||||
|
, class Value = use_default
|
||||||
|
, class CategoryOrTraversal = use_default
|
||||||
|
, class Reference = use_default
|
||||||
|
, class Difference = use_default
|
||||||
|
>
|
||||||
|
class iterator_adaptor
|
||||||
|
: public iterator_facade<Derived, *V'*, *C'*, *R'*, *D'*> // see details__
|
||||||
|
{
|
||||||
|
friend class iterator_core_access;
|
||||||
|
public:
|
||||||
|
iterator_adaptor();
|
||||||
|
explicit iterator_adaptor(Base const& iter);
|
||||||
|
typedef Base base_type;
|
||||||
|
Base const& base() const;
|
||||||
|
protected:
|
||||||
|
typedef iterator_adaptor iterator_adaptor\_;
|
||||||
|
Base const& base_reference() const;
|
||||||
|
Base& base_reference();
|
||||||
|
private: // Core iterator interface for iterator_facade.
|
||||||
|
typename iterator_adaptor::reference dereference() const;
|
||||||
|
|
||||||
|
template <
|
||||||
|
class OtherDerived, class OtherIterator, class V, class C, class R, class D
|
||||||
|
>
|
||||||
|
bool equal(iterator_adaptor<OtherDerived, OtherIterator, V, C, R, D> const& x) const;
|
||||||
|
|
||||||
|
void advance(typename iterator_adaptor::difference_type n);
|
||||||
|
void increment();
|
||||||
|
void decrement();
|
||||||
|
|
||||||
|
template <
|
||||||
|
class OtherDerived, class OtherIterator, class V, class C, class R, class D
|
||||||
|
>
|
||||||
|
typename iterator_adaptor::difference_type distance_to(
|
||||||
|
iterator_adaptor<OtherDerived, OtherIterator, V, C, R, D> const& y) const;
|
||||||
|
|
||||||
|
private:
|
||||||
|
Base m_iterator; // exposition only
|
||||||
|
};
|
||||||
|
|
||||||
|
__ base_parameters_
|
||||||
|
|
||||||
|
.. _requirements:
|
||||||
|
|
||||||
|
``iterator_adaptor`` requirements
|
||||||
|
---------------------------------
|
||||||
|
|
||||||
|
``static_cast<Derived*>(iterator_adaptor*)`` shall be well-formed.
|
||||||
|
The ``Base`` argument shall be Assignable and Copy Constructible.
|
||||||
|
|
||||||
|
|
||||||
|
.. _base_parameters:
|
||||||
|
|
||||||
|
``iterator_adaptor`` base class parameters
|
||||||
|
------------------------------------------
|
||||||
|
|
||||||
|
The *V'*, *C'*, *R'*, and *D'* parameters of the ``iterator_facade``
|
||||||
|
used as a base class in the summary of ``iterator_adaptor``
|
||||||
|
above are defined as follows:
|
||||||
|
|
||||||
|
.. parsed-literal::
|
||||||
|
|
||||||
|
*V'* = if (Value is use_default)
|
||||||
|
return iterator_traits<Base>::value_type
|
||||||
|
else
|
||||||
|
return Value
|
||||||
|
|
||||||
|
*C'* = if (CategoryOrTraversal is use_default)
|
||||||
|
return iterator_traversal<Base>::type
|
||||||
|
else
|
||||||
|
return CategoryOrTraversal
|
||||||
|
|
||||||
|
*R'* = if (Reference is use_default)
|
||||||
|
if (Value is use_default)
|
||||||
|
return iterator_traits<Base>::reference
|
||||||
|
else
|
||||||
|
return Value&
|
||||||
|
else
|
||||||
|
return Reference
|
||||||
|
|
||||||
|
*D'* = if (Difference is use_default)
|
||||||
|
return iterator_traits<Base>::difference_type
|
||||||
|
else
|
||||||
|
return Difference
|
||||||
|
|
||||||
|
.. ``iterator_adaptor`` models
|
||||||
|
---------------------------
|
||||||
|
|
||||||
|
In order for ``Derived`` to model the iterator concepts corresponding
|
||||||
|
to ``iterator_traits<Derived>::iterator_category``, the expressions
|
||||||
|
involving ``m_iterator`` in the specifications of those private member
|
||||||
|
functions of ``iterator_adaptor`` that may be called by
|
||||||
|
``iterator_facade<Derived, V, C, R, D>`` in evaluating any valid
|
||||||
|
expression involving ``Derived`` in those concepts' requirements.
|
||||||
|
|
||||||
|
.. The above is confusing and needs a rewrite. -JGS
|
||||||
|
.. That's why it's removed. We're embracing inheritance, remember?
|
||||||
|
|
||||||
|
``iterator_adaptor`` public operations
|
||||||
|
--------------------------------------
|
||||||
|
|
||||||
|
``iterator_adaptor();``
|
||||||
|
|
||||||
|
:Requires: The ``Base`` type must be Default Constructible.
|
||||||
|
:Returns: An instance of ``iterator_adaptor`` with
|
||||||
|
``m_iterator`` default constructed.
|
||||||
|
|
||||||
|
|
||||||
|
``explicit iterator_adaptor(Base const& iter);``
|
||||||
|
|
||||||
|
:Returns: An instance of ``iterator_adaptor`` with
|
||||||
|
``m_iterator`` copy constructed from ``iter``.
|
||||||
|
|
||||||
|
``Base const& base() const;``
|
||||||
|
|
||||||
|
:Returns: ``m_iterator``
|
||||||
|
|
||||||
|
``iterator_adaptor`` protected member functions
|
||||||
|
-----------------------------------------------
|
||||||
|
|
||||||
|
``Base const& base_reference() const;``
|
||||||
|
|
||||||
|
:Returns: A const reference to ``m_iterator``.
|
||||||
|
|
||||||
|
|
||||||
|
``Base& base_reference();``
|
||||||
|
|
||||||
|
:Returns: A non-const reference to ``m_iterator``.
|
||||||
|
|
||||||
|
|
||||||
|
``iterator_adaptor`` private member functions
|
||||||
|
---------------------------------------------
|
||||||
|
|
||||||
|
``typename iterator_adaptor::reference dereference() const;``
|
||||||
|
|
||||||
|
:Returns: ``*m_iterator``
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <
|
||||||
|
class OtherDerived, class OtherIterator, class V, class C, class R, class D
|
||||||
|
>
|
||||||
|
bool equal(iterator_adaptor<OtherDerived, OtherIterator, V, C, R, D> const& x) const;
|
||||||
|
|
||||||
|
:Returns: ``m_iterator == x.base()``
|
||||||
|
|
||||||
|
|
||||||
|
``void advance(typename iterator_adaptor::difference_type n);``
|
||||||
|
|
||||||
|
:Effects: ``m_iterator += n;``
|
||||||
|
|
||||||
|
``void increment();``
|
||||||
|
|
||||||
|
:Effects: ``++m_iterator;``
|
||||||
|
|
||||||
|
``void decrement();``
|
||||||
|
|
||||||
|
:Effects: ``--m_iterator;``
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <
|
||||||
|
class OtherDerived, class OtherIterator, class V, class C, class R, class D
|
||||||
|
>
|
||||||
|
typename iterator_adaptor::difference_type distance_to(
|
||||||
|
iterator_adaptor<OtherDerived, OtherIterator, V, C, R, D> const& y) const;
|
||||||
|
|
||||||
|
:Returns: ``y.base() - m_iterator``
|
135
doc/iterator_adaptor_tutorial.rst
Normal file
135
doc/iterator_adaptor_tutorial.rst
Normal file
@ -0,0 +1,135 @@
|
|||||||
|
.. Copyright David Abrahams 2004. Use, modification and distribution is
|
||||||
|
.. subject to the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
In this section we'll further refine the ``node_iter`` class
|
||||||
|
template we developed in the |fac_tut|_. If you haven't already
|
||||||
|
read that material, you should go back now and check it out because
|
||||||
|
we're going to pick up right where it left off.
|
||||||
|
|
||||||
|
.. |fac_tut| replace:: ``iterator_facade`` tutorial
|
||||||
|
.. _fac_tut: iterator_facade.html#tutorial-example
|
||||||
|
|
||||||
|
.. sidebar:: ``node_base*`` really *is* an iterator
|
||||||
|
|
||||||
|
It's not really a very interesting iterator, since ``node_base``
|
||||||
|
is an abstract class: a pointer to a ``node_base`` just points
|
||||||
|
at some base subobject of an instance of some other class, and
|
||||||
|
incrementing a ``node_base*`` moves it past this base subobject
|
||||||
|
to who-knows-where? The most we can do with that incremented
|
||||||
|
position is to compare another ``node_base*`` to it. In other
|
||||||
|
words, the original iterator traverses a one-element array.
|
||||||
|
|
||||||
|
You probably didn't think of it this way, but the ``node_base*``
|
||||||
|
object that underlies ``node_iterator`` is itself an iterator,
|
||||||
|
just like all other pointers. If we examine that pointer closely
|
||||||
|
from an iterator perspective, we can see that it has much in common
|
||||||
|
with the ``node_iterator`` we're building. First, they share most
|
||||||
|
of the same associated types (``value_type``, ``reference``,
|
||||||
|
``pointer``, and ``difference_type``). Second, even some of the
|
||||||
|
core functionality is the same: ``operator*`` and ``operator==`` on
|
||||||
|
the ``node_iterator`` return the result of invoking the same
|
||||||
|
operations on the underlying pointer, via the ``node_iterator``\ 's
|
||||||
|
|dereference_and_equal|_). The only real behavioral difference
|
||||||
|
between ``node_base*`` and ``node_iterator`` can be observed when
|
||||||
|
they are incremented: ``node_iterator`` follows the
|
||||||
|
``m_next`` pointer, while ``node_base*`` just applies an address offset.
|
||||||
|
|
||||||
|
.. |dereference_and_equal| replace:: ``dereference`` and ``equal`` member functions
|
||||||
|
.. _dereference_and_equal: iterator_facade.html#implementing-the-core-operations
|
||||||
|
|
||||||
|
It turns out that the pattern of building an iterator on another
|
||||||
|
iterator-like type (the ``Base`` [#base]_ type) while modifying
|
||||||
|
just a few aspects of the underlying type's behavior is an
|
||||||
|
extremely common one, and it's the pattern addressed by
|
||||||
|
``iterator_adaptor``. Using ``iterator_adaptor`` is very much like
|
||||||
|
using ``iterator_facade``, but because iterator_adaptor tries to
|
||||||
|
mimic as much of the ``Base`` type's behavior as possible, we
|
||||||
|
neither have to supply a ``Value`` argument, nor implement any core
|
||||||
|
behaviors other than ``increment``. The implementation of
|
||||||
|
``node_iter`` is thus reduced to::
|
||||||
|
|
||||||
|
template <class Value>
|
||||||
|
class node_iter
|
||||||
|
: public boost::iterator_adaptor<
|
||||||
|
node_iter<Value> // Derived
|
||||||
|
, Value* // Base
|
||||||
|
, boost::use_default // Value
|
||||||
|
, boost::forward_traversal_tag // CategoryOrTraversal
|
||||||
|
>
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
struct enabler {}; // a private type avoids misuse
|
||||||
|
|
||||||
|
public:
|
||||||
|
node_iter()
|
||||||
|
: node_iter::iterator_adaptor_(0) {}
|
||||||
|
|
||||||
|
explicit node_iter(Value* p)
|
||||||
|
: node_iter::iterator_adaptor_(p) {}
|
||||||
|
|
||||||
|
template <class OtherValue>
|
||||||
|
node_iter(
|
||||||
|
node_iter<OtherValue> const& other
|
||||||
|
, typename boost::enable_if<
|
||||||
|
boost::is_convertible<OtherValue*,Value*>
|
||||||
|
, enabler
|
||||||
|
>::type = enabler()
|
||||||
|
)
|
||||||
|
: node_iter::iterator_adaptor_(other.base()) {}
|
||||||
|
|
||||||
|
private:
|
||||||
|
friend class boost::iterator_core_access;
|
||||||
|
void increment() { this->base_reference() = this->base()->next(); }
|
||||||
|
};
|
||||||
|
|
||||||
|
Note the use of ``node_iter::iterator_adaptor_`` here: because
|
||||||
|
``iterator_adaptor`` defines a nested ``iterator_adaptor_`` type
|
||||||
|
that refers to itself, that gives us a convenient way to refer to
|
||||||
|
the complicated base class type of ``node_iter<Value>``. [Note:
|
||||||
|
this technique is known not to work with Borland C++ 5.6.4 and
|
||||||
|
Metrowerks CodeWarrior versions prior to 9.0]
|
||||||
|
|
||||||
|
You can see an example program that exercises this version of the
|
||||||
|
node iterators `here`__.
|
||||||
|
|
||||||
|
__ ../example/node_iterator3.cpp
|
||||||
|
|
||||||
|
In the case of ``node_iter``, it's not very compelling to pass
|
||||||
|
``boost::use_default`` as ``iterator_adaptor``\ 's ``Value``
|
||||||
|
argument; we could have just passed ``node_iter``\ 's ``Value``
|
||||||
|
along to ``iterator_adaptor``, and that'd even be shorter! Most
|
||||||
|
iterator class templates built with ``iterator_adaptor`` are
|
||||||
|
parameterized on another iterator type, rather than on its
|
||||||
|
``value_type``. For example, ``boost::reverse_iterator`` takes an
|
||||||
|
iterator type argument and reverses its direction of traversal,
|
||||||
|
since the original iterator and the reversed one have all the same
|
||||||
|
associated types, ``iterator_adaptor``\ 's delegation of default
|
||||||
|
types to its ``Base`` saves the implementor of
|
||||||
|
``boost::reverse_iterator`` from writing:
|
||||||
|
|
||||||
|
.. parsed-literal::
|
||||||
|
|
||||||
|
std::iterator_traits<Iterator>::*some-associated-type*
|
||||||
|
|
||||||
|
at least four times.
|
||||||
|
|
||||||
|
We urge you to review the documentation and implementations of
|
||||||
|
|reverse_iterator|_ and the other Boost `specialized iterator
|
||||||
|
adaptors`__ to get an idea of the sorts of things you can do with
|
||||||
|
``iterator_adaptor``. In particular, have a look at
|
||||||
|
|transform_iterator|_, which is perhaps the most straightforward
|
||||||
|
adaptor, and also |counting_iterator|_, which demonstrates that
|
||||||
|
``iterator_adaptor``\ 's ``Base`` type needn't be an iterator.
|
||||||
|
|
||||||
|
.. |reverse_iterator| replace:: ``reverse_iterator``
|
||||||
|
.. _reverse_iterator: reverse_iterator.html
|
||||||
|
|
||||||
|
.. |counting_iterator| replace:: ``counting_iterator``
|
||||||
|
.. _counting_iterator: counting_iterator.html
|
||||||
|
|
||||||
|
.. |transform_iterator| replace:: ``transform_iterator``
|
||||||
|
.. _transform_iterator: transform_iterator.html
|
||||||
|
|
||||||
|
__ index.html#specialized-adaptors
|
||||||
|
|
224
doc/iterator_archetypes.html
Normal file
224
doc/iterator_archetypes.html
Normal file
@ -0,0 +1,224 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" />
|
||||||
|
<title>Iterator Archetype</title>
|
||||||
|
<meta name="author" content="David Abrahams, Jeremy Siek, Thomas Witt" />
|
||||||
|
<meta name="organization" content="Boost Consulting, Indiana University Open Systems Lab, Zephyr Associates, Inc." />
|
||||||
|
<meta name="date" content="2006-09-11" />
|
||||||
|
<meta name="copyright" content="Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2004." />
|
||||||
|
<link rel="stylesheet" href="../../../rst.css" type="text/css" />
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="iterator-archetype">
|
||||||
|
<h1 class="title">Iterator Archetype</h1>
|
||||||
|
<table class="docinfo" frame="void" rules="none">
|
||||||
|
<col class="docinfo-name" />
|
||||||
|
<col class="docinfo-content" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><th class="docinfo-name">Author:</th>
|
||||||
|
<td>David Abrahams, Jeremy Siek, Thomas Witt</td></tr>
|
||||||
|
<tr><th class="docinfo-name">Contact:</th>
|
||||||
|
<td><a class="first reference external" href="mailto:dave@boost-consulting.com">dave@boost-consulting.com</a>, <a class="reference external" href="mailto:jsiek@osl.iu.edu">jsiek@osl.iu.edu</a>, <a class="last reference external" href="mailto:witt@styleadvisor.com">witt@styleadvisor.com</a></td></tr>
|
||||||
|
<tr><th class="docinfo-name">Organization:</th>
|
||||||
|
<td><a class="first reference external" href="http://www.boost-consulting.com">Boost Consulting</a>, Indiana University <a class="reference external" href="http://www.osl.iu.edu">Open Systems
|
||||||
|
Lab</a>, <a class="last reference external" href="http://www.styleadvisor.com">Zephyr Associates, Inc.</a></td></tr>
|
||||||
|
<tr><th class="docinfo-name">Date:</th>
|
||||||
|
<td>2006-09-11</td></tr>
|
||||||
|
<tr><th class="docinfo-name">Copyright:</th>
|
||||||
|
<td>Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2004.</td></tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<!-- Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">abstract:</th><td class="field-body">The <tt class="docutils literal"><span class="pre">iterator_archetype</span></tt> class constructs a minimal implementation of
|
||||||
|
one of the iterator access concepts and one of the iterator traversal concepts.
|
||||||
|
This is used for doing a compile-time check to see if a the type requirements
|
||||||
|
of a template are really enough to cover the implementation of the template.
|
||||||
|
For further information see the documentation for the <a class="reference external" href="../../concept_check/index.html"><tt class="docutils literal"><span class="pre">boost::concept_check</span></tt></a> library.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<div class="contents topic" id="table-of-contents">
|
||||||
|
<p class="topic-title first">Table of Contents</p>
|
||||||
|
<ul class="simple">
|
||||||
|
<li><a class="reference internal" href="#reference" id="id1">Reference</a><ul>
|
||||||
|
<li><a class="reference internal" href="#iterator-archetype-synopsis" id="id2"><tt class="docutils literal"><span class="pre">iterator_archetype</span></tt> Synopsis</a></li>
|
||||||
|
<li><a class="reference internal" href="#access-category-tags" id="id3"><tt class="docutils literal"><span class="pre">Access</span> <span class="pre">Category</span> <span class="pre">Tags</span></tt></a></li>
|
||||||
|
<li><a class="reference internal" href="#iterator-archetype-requirements" id="id4"><tt class="docutils literal"><span class="pre">iterator_archetype</span></tt> Requirements</a></li>
|
||||||
|
<li><a class="reference internal" href="#iterator-archetype-models" id="id5"><tt class="docutils literal"><span class="pre">iterator_archetype</span></tt> Models</a></li>
|
||||||
|
<li><a class="reference internal" href="#traits" id="id6"><tt class="docutils literal"><span class="pre">Traits</span></tt></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="reference">
|
||||||
|
<h1><a class="toc-backref" href="#id1">Reference</a></h1>
|
||||||
|
<div class="section" id="iterator-archetype-synopsis">
|
||||||
|
<h2><a class="toc-backref" href="#id2"><tt class="docutils literal"><span class="pre">iterator_archetype</span></tt> Synopsis</a></h2>
|
||||||
|
<pre class="literal-block">
|
||||||
|
namespace iterator_archetypes
|
||||||
|
{
|
||||||
|
// Access categories
|
||||||
|
|
||||||
|
typedef /*implementation defined*/ readable_iterator_t;
|
||||||
|
typedef /*implementation defined*/ writable_iterator_t;
|
||||||
|
typedef /*implementation defined*/ readable_writable_iterator_t;
|
||||||
|
typedef /*implementation defined*/ readable_lvalue_iterator_t;
|
||||||
|
typedef /*implementation defined*/ writable_lvalue_iterator_t;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
template <
|
||||||
|
class Value
|
||||||
|
, class AccessCategory
|
||||||
|
, class TraversalCategory
|
||||||
|
>
|
||||||
|
class iterator_archetype
|
||||||
|
{
|
||||||
|
typedef /* see below */ value_type;
|
||||||
|
typedef /* see below */ reference;
|
||||||
|
typedef /* see below */ pointer;
|
||||||
|
typedef /* see below */ difference_type;
|
||||||
|
typedef /* see below */ iterator_category;
|
||||||
|
};
|
||||||
|
</pre>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="access-category-tags">
|
||||||
|
<h2><a class="toc-backref" href="#id3"><tt class="docutils literal"><span class="pre">Access</span> <span class="pre">Category</span> <span class="pre">Tags</span></tt></a></h2>
|
||||||
|
<p>The access category types provided correspond to the following
|
||||||
|
standard iterator access concept combinations:</p>
|
||||||
|
<pre class="literal-block">
|
||||||
|
readable_iterator_t :=
|
||||||
|
|
||||||
|
Readable Iterator
|
||||||
|
|
||||||
|
writable_iterator_t :=
|
||||||
|
|
||||||
|
Writeable Iterator
|
||||||
|
|
||||||
|
readable_writable_iterator_t :=
|
||||||
|
|
||||||
|
Readable Iterator & Writeable Iterator & Swappable Iterator
|
||||||
|
|
||||||
|
readable_lvalue_iterator_t :=
|
||||||
|
|
||||||
|
Readable Iterator & Lvalue Iterator
|
||||||
|
|
||||||
|
writeable_lvalue_iterator_t :=
|
||||||
|
|
||||||
|
Readable Iterator & Writeable Iterator & Swappable Iterator & Lvalue Iterator
|
||||||
|
</pre>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="iterator-archetype-requirements">
|
||||||
|
<h2><a class="toc-backref" href="#id4"><tt class="docutils literal"><span class="pre">iterator_archetype</span></tt> Requirements</a></h2>
|
||||||
|
<p>The <tt class="docutils literal"><span class="pre">AccessCategory</span></tt> argument must be one of the predefined access
|
||||||
|
category tags. The <tt class="docutils literal"><span class="pre">TraversalCategory</span></tt> must be one of the standard
|
||||||
|
traversal tags. The <tt class="docutils literal"><span class="pre">Value</span></tt> type must satisfy the requirements of
|
||||||
|
the iterator concept specified by <tt class="docutils literal"><span class="pre">AccessCategory</span></tt> and
|
||||||
|
<tt class="docutils literal"><span class="pre">TraversalCategory</span></tt> as implied by the nested traits types.</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="iterator-archetype-models">
|
||||||
|
<h2><a class="toc-backref" href="#id5"><tt class="docutils literal"><span class="pre">iterator_archetype</span></tt> Models</a></h2>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">iterator_archetype</span></tt> models the iterator concepts specified by the
|
||||||
|
<tt class="docutils literal"><span class="pre">AccessCategory</span></tt> and <tt class="docutils literal"><span class="pre">TraversalCategory</span></tt>
|
||||||
|
arguments. <tt class="docutils literal"><span class="pre">iterator_archetype</span></tt> does not model any other access
|
||||||
|
concepts or any more derived traversal concepts.</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="traits">
|
||||||
|
<h2><a class="toc-backref" href="#id6"><tt class="docutils literal"><span class="pre">Traits</span></tt></a></h2>
|
||||||
|
<p>The nested trait types are defined as follows:</p>
|
||||||
|
<pre class="literal-block">
|
||||||
|
if (AccessCategory == readable_iterator_t)
|
||||||
|
|
||||||
|
value_type = Value
|
||||||
|
reference = Value
|
||||||
|
pointer = Value*
|
||||||
|
|
||||||
|
else if (AccessCategory == writable_iterator_t)
|
||||||
|
|
||||||
|
value_type = void
|
||||||
|
reference = void
|
||||||
|
pointer = void
|
||||||
|
|
||||||
|
else if (AccessCategory == readable_writable_iterator_t)
|
||||||
|
|
||||||
|
value_type = Value
|
||||||
|
|
||||||
|
reference :=
|
||||||
|
|
||||||
|
A type X that is convertible to Value for which the following
|
||||||
|
expression is valid. Given an object x of type X and v of type
|
||||||
|
Value.
|
||||||
|
|
||||||
|
x = v
|
||||||
|
|
||||||
|
pointer = Value*
|
||||||
|
|
||||||
|
else if (AccessCategory == readable_lvalue_iterator_t)
|
||||||
|
|
||||||
|
value_type = Value
|
||||||
|
reference = Value const&
|
||||||
|
pointer = Value const*
|
||||||
|
|
||||||
|
else if (AccessCategory == writable_lvalue_iterator_t)
|
||||||
|
|
||||||
|
value_type = Value
|
||||||
|
reference = Value&
|
||||||
|
pointer = Value*
|
||||||
|
|
||||||
|
if ( TraversalCategory is convertible to forward_traversal_tag )
|
||||||
|
|
||||||
|
difference_type := ptrdiff_t
|
||||||
|
|
||||||
|
else
|
||||||
|
|
||||||
|
difference_type := unspecified type
|
||||||
|
|
||||||
|
|
||||||
|
iterator_category :=
|
||||||
|
|
||||||
|
A type X satisfying the following two constraints:
|
||||||
|
|
||||||
|
1. X is convertible to X1, and not to any more-derived
|
||||||
|
type, where X1 is defined by:
|
||||||
|
|
||||||
|
if (reference is a reference type
|
||||||
|
&& TraversalCategory is convertible to forward_traversal_tag)
|
||||||
|
{
|
||||||
|
if (TraversalCategory is convertible to random_access_traversal_tag)
|
||||||
|
X1 = random_access_iterator_tag
|
||||||
|
else if (TraversalCategory is convertible to bidirectional_traversal_tag)
|
||||||
|
X1 = bidirectional_iterator_tag
|
||||||
|
else
|
||||||
|
X1 = forward_iterator_tag
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (TraversalCategory is convertible to single_pass_traversal_tag
|
||||||
|
&& reference != void)
|
||||||
|
X1 = input_iterator_tag
|
||||||
|
else
|
||||||
|
X1 = output_iterator_tag
|
||||||
|
}
|
||||||
|
|
||||||
|
2. X is convertible to TraversalCategory
|
||||||
|
</pre>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<hr class="footer" />
|
||||||
|
<a class="reference external" href="iterator_archetypes.rst">View document source</a>.
|
||||||
|
Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
BIN
doc/iterator_archetypes.pdf
Normal file
BIN
doc/iterator_archetypes.pdf
Normal file
Binary file not shown.
193
doc/iterator_archetypes.rst
Normal file
193
doc/iterator_archetypes.rst
Normal file
@ -0,0 +1,193 @@
|
|||||||
|
.. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
++++++++++++++++++++
|
||||||
|
Iterator Archetype
|
||||||
|
++++++++++++++++++++
|
||||||
|
|
||||||
|
:Author: David Abrahams, Jeremy Siek, Thomas Witt
|
||||||
|
:Contact: dave@boost-consulting.com, jsiek@osl.iu.edu, witt@styleadvisor.com
|
||||||
|
:organization: `Boost Consulting`_, Indiana University `Open Systems
|
||||||
|
Lab`_, `Zephyr Associates, Inc.`_
|
||||||
|
:date: $Date$
|
||||||
|
:copyright: Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2004.
|
||||||
|
|
||||||
|
.. _`Boost Consulting`: http://www.boost-consulting.com
|
||||||
|
.. _`Open Systems Lab`: http://www.osl.iu.edu
|
||||||
|
.. _`Zephyr Associates, Inc.`: http://www.styleadvisor.com
|
||||||
|
|
||||||
|
:abstract: The ``iterator_archetype`` class constructs a minimal implementation of
|
||||||
|
one of the iterator access concepts and one of the iterator traversal concepts.
|
||||||
|
This is used for doing a compile-time check to see if a the type requirements
|
||||||
|
of a template are really enough to cover the implementation of the template.
|
||||||
|
For further information see the documentation for the |concepts|_ library.
|
||||||
|
|
||||||
|
.. |concepts| replace:: ``boost::concept_check``
|
||||||
|
.. _concepts: ../../concept_check/index.html
|
||||||
|
|
||||||
|
|
||||||
|
.. contents:: Table of Contents
|
||||||
|
|
||||||
|
Reference
|
||||||
|
=========
|
||||||
|
|
||||||
|
``iterator_archetype`` Synopsis
|
||||||
|
...............................
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
namespace iterator_archetypes
|
||||||
|
{
|
||||||
|
// Access categories
|
||||||
|
|
||||||
|
typedef /*implementation defined*/ readable_iterator_t;
|
||||||
|
typedef /*implementation defined*/ writable_iterator_t;
|
||||||
|
typedef /*implementation defined*/ readable_writable_iterator_t;
|
||||||
|
typedef /*implementation defined*/ readable_lvalue_iterator_t;
|
||||||
|
typedef /*implementation defined*/ writable_lvalue_iterator_t;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
template <
|
||||||
|
class Value
|
||||||
|
, class AccessCategory
|
||||||
|
, class TraversalCategory
|
||||||
|
>
|
||||||
|
class iterator_archetype
|
||||||
|
{
|
||||||
|
typedef /* see below */ value_type;
|
||||||
|
typedef /* see below */ reference;
|
||||||
|
typedef /* see below */ pointer;
|
||||||
|
typedef /* see below */ difference_type;
|
||||||
|
typedef /* see below */ iterator_category;
|
||||||
|
};
|
||||||
|
|
||||||
|
``Access Category Tags``
|
||||||
|
........................
|
||||||
|
|
||||||
|
The access category types provided correspond to the following
|
||||||
|
standard iterator access concept combinations:
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
readable_iterator_t :=
|
||||||
|
|
||||||
|
Readable Iterator
|
||||||
|
|
||||||
|
writable_iterator_t :=
|
||||||
|
|
||||||
|
Writeable Iterator
|
||||||
|
|
||||||
|
readable_writable_iterator_t :=
|
||||||
|
|
||||||
|
Readable Iterator & Writeable Iterator & Swappable Iterator
|
||||||
|
|
||||||
|
readable_lvalue_iterator_t :=
|
||||||
|
|
||||||
|
Readable Iterator & Lvalue Iterator
|
||||||
|
|
||||||
|
writeable_lvalue_iterator_t :=
|
||||||
|
|
||||||
|
Readable Iterator & Writeable Iterator & Swappable Iterator & Lvalue Iterator
|
||||||
|
|
||||||
|
``iterator_archetype`` Requirements
|
||||||
|
...................................
|
||||||
|
|
||||||
|
The ``AccessCategory`` argument must be one of the predefined access
|
||||||
|
category tags. The ``TraversalCategory`` must be one of the standard
|
||||||
|
traversal tags. The ``Value`` type must satisfy the requirements of
|
||||||
|
the iterator concept specified by ``AccessCategory`` and
|
||||||
|
``TraversalCategory`` as implied by the nested traits types.
|
||||||
|
|
||||||
|
``iterator_archetype`` Models
|
||||||
|
.............................
|
||||||
|
|
||||||
|
``iterator_archetype`` models the iterator concepts specified by the
|
||||||
|
``AccessCategory`` and ``TraversalCategory``
|
||||||
|
arguments. ``iterator_archetype`` does not model any other access
|
||||||
|
concepts or any more derived traversal concepts.
|
||||||
|
|
||||||
|
``Traits``
|
||||||
|
..........
|
||||||
|
|
||||||
|
The nested trait types are defined as follows:
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
if (AccessCategory == readable_iterator_t)
|
||||||
|
|
||||||
|
value_type = Value
|
||||||
|
reference = Value
|
||||||
|
pointer = Value*
|
||||||
|
|
||||||
|
else if (AccessCategory == writable_iterator_t)
|
||||||
|
|
||||||
|
value_type = void
|
||||||
|
reference = void
|
||||||
|
pointer = void
|
||||||
|
|
||||||
|
else if (AccessCategory == readable_writable_iterator_t)
|
||||||
|
|
||||||
|
value_type = Value
|
||||||
|
|
||||||
|
reference :=
|
||||||
|
|
||||||
|
A type X that is convertible to Value for which the following
|
||||||
|
expression is valid. Given an object x of type X and v of type
|
||||||
|
Value.
|
||||||
|
|
||||||
|
x = v
|
||||||
|
|
||||||
|
pointer = Value*
|
||||||
|
|
||||||
|
else if (AccessCategory == readable_lvalue_iterator_t)
|
||||||
|
|
||||||
|
value_type = Value
|
||||||
|
reference = Value const&
|
||||||
|
pointer = Value const*
|
||||||
|
|
||||||
|
else if (AccessCategory == writable_lvalue_iterator_t)
|
||||||
|
|
||||||
|
value_type = Value
|
||||||
|
reference = Value&
|
||||||
|
pointer = Value*
|
||||||
|
|
||||||
|
if ( TraversalCategory is convertible to forward_traversal_tag )
|
||||||
|
|
||||||
|
difference_type := ptrdiff_t
|
||||||
|
|
||||||
|
else
|
||||||
|
|
||||||
|
difference_type := unspecified type
|
||||||
|
|
||||||
|
|
||||||
|
iterator_category :=
|
||||||
|
|
||||||
|
A type X satisfying the following two constraints:
|
||||||
|
|
||||||
|
1. X is convertible to X1, and not to any more-derived
|
||||||
|
type, where X1 is defined by:
|
||||||
|
|
||||||
|
if (reference is a reference type
|
||||||
|
&& TraversalCategory is convertible to forward_traversal_tag)
|
||||||
|
{
|
||||||
|
if (TraversalCategory is convertible to random_access_traversal_tag)
|
||||||
|
X1 = random_access_iterator_tag
|
||||||
|
else if (TraversalCategory is convertible to bidirectional_traversal_tag)
|
||||||
|
X1 = bidirectional_iterator_tag
|
||||||
|
else
|
||||||
|
X1 = forward_iterator_tag
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (TraversalCategory is convertible to single_pass_traversal_tag
|
||||||
|
&& reference != void)
|
||||||
|
X1 = input_iterator_tag
|
||||||
|
else
|
||||||
|
X1 = output_iterator_tag
|
||||||
|
}
|
||||||
|
|
||||||
|
2. X is convertible to TraversalCategory
|
||||||
|
|
||||||
|
|
127
doc/iterator_concepts.html
Normal file
127
doc/iterator_concepts.html
Normal file
@ -0,0 +1,127 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" />
|
||||||
|
<title>Iterator Concepts</title>
|
||||||
|
<meta name="author" content="David Abrahams, Jeremy Siek, Thomas Witt" />
|
||||||
|
<meta name="organization" content="Boost Consulting, Indiana University Open Systems Lab, Zephyr Associates, Inc." />
|
||||||
|
<meta name="date" content="2006-09-11" />
|
||||||
|
<meta name="copyright" content="Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2004." />
|
||||||
|
<link rel="stylesheet" href="../../../rst.css" type="text/css" />
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="iterator-concepts">
|
||||||
|
<h1 class="title">Iterator Concepts</h1>
|
||||||
|
<table class="docinfo" frame="void" rules="none">
|
||||||
|
<col class="docinfo-name" />
|
||||||
|
<col class="docinfo-content" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><th class="docinfo-name">Author:</th>
|
||||||
|
<td>David Abrahams, Jeremy Siek, Thomas Witt</td></tr>
|
||||||
|
<tr><th class="docinfo-name">Contact:</th>
|
||||||
|
<td><a class="first reference external" href="mailto:dave@boost-consulting.com">dave@boost-consulting.com</a>, <a class="reference external" href="mailto:jsiek@osl.iu.edu">jsiek@osl.iu.edu</a>, <a class="last reference external" href="mailto:witt@styleadvisor.com">witt@styleadvisor.com</a></td></tr>
|
||||||
|
<tr><th class="docinfo-name">Organization:</th>
|
||||||
|
<td><a class="first reference external" href="http://www.boost-consulting.com">Boost Consulting</a>, Indiana University <a class="reference external" href="http://www.osl.iu.edu">Open Systems
|
||||||
|
Lab</a>, <a class="last reference external" href="http://www.styleadvisor.com">Zephyr Associates, Inc.</a></td></tr>
|
||||||
|
<tr><th class="docinfo-name">Date:</th>
|
||||||
|
<td>2006-09-11</td></tr>
|
||||||
|
<tr><th class="docinfo-name">Copyright:</th>
|
||||||
|
<td>Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2004.</td></tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<!-- Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">abstract:</th><td class="field-body">The iterator concept checking classes provide a mechanism for
|
||||||
|
a template to report better error messages when a user instantiates
|
||||||
|
the template with a type that does not meet the requirements of
|
||||||
|
the template.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p>For an introduction to using concept checking classes, see
|
||||||
|
the documentation for the <a class="reference external" href="../../concept_check/index.html"><tt class="docutils literal"><span class="pre">boost::concept_check</span></tt></a> library.</p>
|
||||||
|
<div class="section" id="reference">
|
||||||
|
<h1>Reference</h1>
|
||||||
|
<div class="section" id="iterator-access-concepts">
|
||||||
|
<h2>Iterator Access Concepts</h2>
|
||||||
|
<ul class="simple">
|
||||||
|
<li><a class="reference external" href="ReadableIterator.html"><em>Readable Iterator</em></a></li>
|
||||||
|
<li><a class="reference external" href="WritableIterator.html"><em>Writable Iterator</em></a></li>
|
||||||
|
<li><a class="reference external" href="SwappableIterator.html"><em>Swappable Iterator</em></a></li>
|
||||||
|
<li><a class="reference external" href="LvalueIterator.html"><em>Lvalue Iterator</em></a></li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="iterator-traversal-concepts">
|
||||||
|
<h2>Iterator Traversal Concepts</h2>
|
||||||
|
<ul class="simple">
|
||||||
|
<li><a class="reference external" href="IncrementableIterator.html"><em>Incrementable Iterator</em></a></li>
|
||||||
|
<li><a class="reference external" href="SinglePassIterator.html"><em>Single Pass Iterator</em></a></li>
|
||||||
|
<li><a class="reference external" href="ForwardTraversal.html"><em>Forward Traversal</em></a></li>
|
||||||
|
<li><a class="reference external" href="BidirectionalTraversal.html"><em>Bidirectional Traversal</em></a></li>
|
||||||
|
<li><a class="reference external" href="RandomAccessTraversal.html"><em>Random Access Traversal</em></a></li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="iterator-concepts-hpp-synopsis">
|
||||||
|
<h2><tt class="docutils literal"><span class="pre">iterator_concepts.hpp</span></tt> Synopsis</h2>
|
||||||
|
<pre class="literal-block">
|
||||||
|
namespace boost_concepts {
|
||||||
|
|
||||||
|
// Iterator Access Concepts
|
||||||
|
|
||||||
|
template <typename Iterator>
|
||||||
|
class ReadableIteratorConcept;
|
||||||
|
|
||||||
|
template <
|
||||||
|
typename Iterator
|
||||||
|
, typename ValueType = std::iterator_traits<Iterator>::value_type
|
||||||
|
>
|
||||||
|
class WritableIteratorConcept;
|
||||||
|
|
||||||
|
template <typename Iterator>
|
||||||
|
class SwappableIteratorConcept;
|
||||||
|
|
||||||
|
template <typename Iterator>
|
||||||
|
class LvalueIteratorConcept;
|
||||||
|
|
||||||
|
// Iterator Traversal Concepts
|
||||||
|
|
||||||
|
template <typename Iterator>
|
||||||
|
class IncrementableIteratorConcept;
|
||||||
|
|
||||||
|
template <typename Iterator>
|
||||||
|
class SinglePassIteratorConcept;
|
||||||
|
|
||||||
|
template <typename Iterator>
|
||||||
|
class ForwardTraversalConcept;
|
||||||
|
|
||||||
|
template <typename Iterator>
|
||||||
|
class BidirectionalTraversalConcept;
|
||||||
|
|
||||||
|
template <typename Iterator>
|
||||||
|
class RandomAccessTraversalConcept;
|
||||||
|
|
||||||
|
// Interoperability
|
||||||
|
|
||||||
|
template <typename Iterator, typename ConstIterator>
|
||||||
|
class InteroperableIteratorConcept;
|
||||||
|
|
||||||
|
}
|
||||||
|
</pre>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<hr class="footer" />
|
||||||
|
<a class="reference external" href="iterator_concepts.rst">View document source</a>.
|
||||||
|
Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
BIN
doc/iterator_concepts.pdf
Normal file
BIN
doc/iterator_concepts.pdf
Normal file
Binary file not shown.
130
doc/iterator_concepts.rst
Normal file
130
doc/iterator_concepts.rst
Normal file
@ -0,0 +1,130 @@
|
|||||||
|
.. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
++++++++++++++++++
|
||||||
|
Iterator Concepts
|
||||||
|
++++++++++++++++++
|
||||||
|
|
||||||
|
:Author: David Abrahams, Jeremy Siek, Thomas Witt
|
||||||
|
:Contact: dave@boost-consulting.com, jsiek@osl.iu.edu, witt@styleadvisor.com
|
||||||
|
:organization: `Boost Consulting`_, Indiana University `Open Systems
|
||||||
|
Lab`_, `Zephyr Associates, Inc.`_
|
||||||
|
:date: $Date$
|
||||||
|
:copyright: Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2004.
|
||||||
|
|
||||||
|
.. _`Boost Consulting`: http://www.boost-consulting.com
|
||||||
|
.. _`Open Systems Lab`: http://www.osl.iu.edu
|
||||||
|
.. _`Zephyr Associates, Inc.`: http://www.styleadvisor.com
|
||||||
|
|
||||||
|
:abstract: The iterator concept checking classes provide a mechanism for
|
||||||
|
a template to report better error messages when a user instantiates
|
||||||
|
the template with a type that does not meet the requirements of
|
||||||
|
the template.
|
||||||
|
|
||||||
|
|
||||||
|
For an introduction to using concept checking classes, see
|
||||||
|
the documentation for the |concepts|_ library.
|
||||||
|
|
||||||
|
.. |concepts| replace:: ``boost::concept_check``
|
||||||
|
.. _concepts: ../../concept_check/index.html
|
||||||
|
|
||||||
|
|
||||||
|
Reference
|
||||||
|
=========
|
||||||
|
|
||||||
|
Iterator Access Concepts
|
||||||
|
........................
|
||||||
|
|
||||||
|
* |Readable|_
|
||||||
|
* |Writable|_
|
||||||
|
* |Swappable|_
|
||||||
|
* |Lvalue|_
|
||||||
|
|
||||||
|
.. |Readable| replace:: *Readable Iterator*
|
||||||
|
.. _Readable: ReadableIterator.html
|
||||||
|
|
||||||
|
.. |Writable| replace:: *Writable Iterator*
|
||||||
|
.. _Writable: WritableIterator.html
|
||||||
|
|
||||||
|
.. |Swappable| replace:: *Swappable Iterator*
|
||||||
|
.. _Swappable: SwappableIterator.html
|
||||||
|
|
||||||
|
.. |Lvalue| replace:: *Lvalue Iterator*
|
||||||
|
.. _Lvalue: LvalueIterator.html
|
||||||
|
|
||||||
|
|
||||||
|
Iterator Traversal Concepts
|
||||||
|
...........................
|
||||||
|
|
||||||
|
* |Incrementable|_
|
||||||
|
* |SinglePass|_
|
||||||
|
* |Forward|_
|
||||||
|
* |Bidir|_
|
||||||
|
* |Random|_
|
||||||
|
|
||||||
|
|
||||||
|
.. |Incrementable| replace:: *Incrementable Iterator*
|
||||||
|
.. _Incrementable: IncrementableIterator.html
|
||||||
|
|
||||||
|
.. |SinglePass| replace:: *Single Pass Iterator*
|
||||||
|
.. _SinglePass: SinglePassIterator.html
|
||||||
|
|
||||||
|
.. |Forward| replace:: *Forward Traversal*
|
||||||
|
.. _Forward: ForwardTraversal.html
|
||||||
|
|
||||||
|
.. |Bidir| replace:: *Bidirectional Traversal*
|
||||||
|
.. _Bidir: BidirectionalTraversal.html
|
||||||
|
|
||||||
|
.. |Random| replace:: *Random Access Traversal*
|
||||||
|
.. _Random: RandomAccessTraversal.html
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
``iterator_concepts.hpp`` Synopsis
|
||||||
|
..................................
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
namespace boost_concepts {
|
||||||
|
|
||||||
|
// Iterator Access Concepts
|
||||||
|
|
||||||
|
template <typename Iterator>
|
||||||
|
class ReadableIteratorConcept;
|
||||||
|
|
||||||
|
template <
|
||||||
|
typename Iterator
|
||||||
|
, typename ValueType = std::iterator_traits<Iterator>::value_type
|
||||||
|
>
|
||||||
|
class WritableIteratorConcept;
|
||||||
|
|
||||||
|
template <typename Iterator>
|
||||||
|
class SwappableIteratorConcept;
|
||||||
|
|
||||||
|
template <typename Iterator>
|
||||||
|
class LvalueIteratorConcept;
|
||||||
|
|
||||||
|
// Iterator Traversal Concepts
|
||||||
|
|
||||||
|
template <typename Iterator>
|
||||||
|
class IncrementableIteratorConcept;
|
||||||
|
|
||||||
|
template <typename Iterator>
|
||||||
|
class SinglePassIteratorConcept;
|
||||||
|
|
||||||
|
template <typename Iterator>
|
||||||
|
class ForwardTraversalConcept;
|
||||||
|
|
||||||
|
template <typename Iterator>
|
||||||
|
class BidirectionalTraversalConcept;
|
||||||
|
|
||||||
|
template <typename Iterator>
|
||||||
|
class RandomAccessTraversalConcept;
|
||||||
|
|
||||||
|
// Interoperability
|
||||||
|
|
||||||
|
template <typename Iterator, typename ConstIterator>
|
||||||
|
class InteroperableIteratorConcept;
|
||||||
|
|
||||||
|
}
|
1348
doc/iterator_facade.html
Normal file
1348
doc/iterator_facade.html
Normal file
File diff suppressed because it is too large
Load Diff
BIN
doc/iterator_facade.pdf
Normal file
BIN
doc/iterator_facade.pdf
Normal file
Binary file not shown.
44
doc/iterator_facade.rst
Normal file
44
doc/iterator_facade.rst
Normal file
@ -0,0 +1,44 @@
|
|||||||
|
.. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
++++++++++++++++
|
||||||
|
Iterator Facade
|
||||||
|
++++++++++++++++
|
||||||
|
|
||||||
|
:Author: David Abrahams, Jeremy Siek, Thomas Witt
|
||||||
|
:Contact: dave@boost-consulting.com, jsiek@osl.iu.edu, witt@ive.uni-hannover.de
|
||||||
|
:organization: `Boost Consulting`_, Indiana University `Open Systems
|
||||||
|
Lab`_, University of Hanover `Institute for Transport
|
||||||
|
Railway Operation and Construction`_
|
||||||
|
:date: $Date$
|
||||||
|
:copyright: Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003.
|
||||||
|
|
||||||
|
.. _`Boost Consulting`: http://www.boost-consulting.com
|
||||||
|
.. _`Open Systems Lab`: http://www.osl.iu.edu
|
||||||
|
.. _`Institute for Transport Railway Operation and Construction`: http://www.ive.uni-hannover.de
|
||||||
|
|
||||||
|
:abstract:
|
||||||
|
|
||||||
|
.. include:: iterator_facade_abstract.rst
|
||||||
|
|
||||||
|
.. contents:: Table of Contents
|
||||||
|
|
||||||
|
Overview
|
||||||
|
========
|
||||||
|
|
||||||
|
.. include:: iterator_facade_body.rst
|
||||||
|
|
||||||
|
|
||||||
|
Reference
|
||||||
|
=========
|
||||||
|
|
||||||
|
.. include:: iterator_facade_ref.rst
|
||||||
|
|
||||||
|
.. _counting: counting_iterator.html
|
||||||
|
|
||||||
|
Tutorial Example
|
||||||
|
================
|
||||||
|
|
||||||
|
.. include:: iterator_facade_tutorial.rst
|
||||||
|
|
8
doc/iterator_facade_abstract.rst
Normal file
8
doc/iterator_facade_abstract.rst
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
``iterator_facade`` is a base class template that implements the
|
||||||
|
interface of standard iterators in terms of a few core functions
|
||||||
|
and associated types, to be supplied by a derived iterator class.
|
||||||
|
|
195
doc/iterator_facade_body.rst
Normal file
195
doc/iterator_facade_body.rst
Normal file
@ -0,0 +1,195 @@
|
|||||||
|
.. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
.. Version 1.1 of this ReStructuredText document corresponds to
|
||||||
|
n1530_, the paper accepted by the LWG for TR1.
|
||||||
|
|
||||||
|
.. Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003.
|
||||||
|
|
||||||
|
|
||||||
|
While the iterator interface is rich, there is a core subset of the
|
||||||
|
interface that is necessary for all the functionality. We have
|
||||||
|
identified the following core behaviors for iterators:
|
||||||
|
|
||||||
|
* dereferencing
|
||||||
|
* incrementing
|
||||||
|
* decrementing
|
||||||
|
* equality comparison
|
||||||
|
* random-access motion
|
||||||
|
* distance measurement
|
||||||
|
|
||||||
|
In addition to the behaviors listed above, the core interface elements
|
||||||
|
include the associated types exposed through iterator traits:
|
||||||
|
``value_type``, ``reference``, ``difference_type``, and
|
||||||
|
``iterator_category``.
|
||||||
|
|
||||||
|
Iterator facade uses the Curiously Recurring Template
|
||||||
|
Pattern (CRTP) [Cop95]_ so that the user can specify the behavior
|
||||||
|
of ``iterator_facade`` in a derived class. Former designs used
|
||||||
|
policy objects to specify the behavior, but that approach was
|
||||||
|
discarded for several reasons:
|
||||||
|
|
||||||
|
1. the creation and eventual copying of the policy object may create
|
||||||
|
overhead that can be avoided with the current approach.
|
||||||
|
|
||||||
|
2. The policy object approach does not allow for custom constructors
|
||||||
|
on the created iterator types, an essential feature if
|
||||||
|
``iterator_facade`` should be used in other library
|
||||||
|
implementations.
|
||||||
|
|
||||||
|
3. Without the use of CRTP, the standard requirement that an
|
||||||
|
iterator's ``operator++`` returns the iterator type itself
|
||||||
|
would mean that all iterators built with the library would
|
||||||
|
have to be specializations of ``iterator_facade<...>``, rather
|
||||||
|
than something more descriptive like
|
||||||
|
``indirect_iterator<T*>``. Cumbersome type generator
|
||||||
|
metafunctions would be needed to build new parameterized
|
||||||
|
iterators, and a separate ``iterator_adaptor`` layer would be
|
||||||
|
impossible.
|
||||||
|
|
||||||
|
Usage
|
||||||
|
-----
|
||||||
|
|
||||||
|
The user of ``iterator_facade`` derives his iterator class from a
|
||||||
|
specialization of ``iterator_facade`` and passes the derived
|
||||||
|
iterator class as ``iterator_facade``\ 's first template parameter.
|
||||||
|
The order of the other template parameters have been carefully
|
||||||
|
chosen to take advantage of useful defaults. For example, when
|
||||||
|
defining a constant lvalue iterator, the user can pass a
|
||||||
|
const-qualified version of the iterator's ``value_type`` as
|
||||||
|
``iterator_facade``\ 's ``Value`` parameter and omit the
|
||||||
|
``Reference`` parameter which follows.
|
||||||
|
|
||||||
|
The derived iterator class must define member functions implementing
|
||||||
|
the iterator's core behaviors. The following table describes
|
||||||
|
expressions which are required to be valid depending on the category
|
||||||
|
of the derived iterator type. These member functions are described
|
||||||
|
briefly below and in more detail in the iterator facade
|
||||||
|
requirements.
|
||||||
|
|
||||||
|
+------------------------+-------------------------------+
|
||||||
|
|Expression |Effects |
|
||||||
|
+========================+===============================+
|
||||||
|
|``i.dereference()`` |Access the value referred to |
|
||||||
|
+------------------------+-------------------------------+
|
||||||
|
|``i.equal(j)`` |Compare for equality with ``j``|
|
||||||
|
+------------------------+-------------------------------+
|
||||||
|
|``i.increment()`` |Advance by one position |
|
||||||
|
+------------------------+-------------------------------+
|
||||||
|
|``i.decrement()`` |Retreat by one position |
|
||||||
|
+------------------------+-------------------------------+
|
||||||
|
|``i.advance(n)`` |Advance by ``n`` positions |
|
||||||
|
+------------------------+-------------------------------+
|
||||||
|
|``i.distance_to(j)`` |Measure the distance to ``j`` |
|
||||||
|
+------------------------+-------------------------------+
|
||||||
|
|
||||||
|
.. Should we add a comment that a zero overhead implementation of iterator_facade
|
||||||
|
is possible with proper inlining?
|
||||||
|
|
||||||
|
In addition to implementing the core interface functions, an iterator
|
||||||
|
derived from ``iterator_facade`` typically defines several
|
||||||
|
constructors. To model any of the standard iterator concepts, the
|
||||||
|
iterator must at least have a copy constructor. Also, if the iterator
|
||||||
|
type ``X`` is meant to be automatically interoperate with another
|
||||||
|
iterator type ``Y`` (as with constant and mutable iterators) then
|
||||||
|
there must be an implicit conversion from ``X`` to ``Y`` or from ``Y``
|
||||||
|
to ``X`` (but not both), typically implemented as a conversion
|
||||||
|
constructor. Finally, if the iterator is to model Forward Traversal
|
||||||
|
Iterator or a more-refined iterator concept, a default constructor is
|
||||||
|
required.
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
Iterator Core Access
|
||||||
|
--------------------
|
||||||
|
|
||||||
|
``iterator_facade`` and the operator implementations need to be able
|
||||||
|
to access the core member functions in the derived class. Making the
|
||||||
|
core member functions public would expose an implementation detail to
|
||||||
|
the user. The design used here ensures that implementation details do
|
||||||
|
not appear in the public interface of the derived iterator type.
|
||||||
|
|
||||||
|
Preventing direct access to the core member functions has two
|
||||||
|
advantages. First, there is no possibility for the user to accidently
|
||||||
|
use a member function of the iterator when a member of the value_type
|
||||||
|
was intended. This has been an issue with smart pointer
|
||||||
|
implementations in the past. The second and main advantage is that
|
||||||
|
library implementers can freely exchange a hand-rolled iterator
|
||||||
|
implementation for one based on ``iterator_facade`` without fear of
|
||||||
|
breaking code that was accessing the public core member functions
|
||||||
|
directly.
|
||||||
|
|
||||||
|
In a naive implementation, keeping the derived class' core member
|
||||||
|
functions private would require it to grant friendship to
|
||||||
|
``iterator_facade`` and each of the seven operators. In order to
|
||||||
|
reduce the burden of limiting access, ``iterator_core_access`` is
|
||||||
|
provided, a class that acts as a gateway to the core member functions
|
||||||
|
in the derived iterator class. The author of the derived class only
|
||||||
|
needs to grant friendship to ``iterator_core_access`` to make his core
|
||||||
|
member functions available to the library.
|
||||||
|
|
||||||
|
.. This is no long uptodate -thw
|
||||||
|
.. Yes it is; I made sure of it! -DWA
|
||||||
|
|
||||||
|
``iterator_core_access`` will be typically implemented as an empty
|
||||||
|
class containing only private static member functions which invoke the
|
||||||
|
iterator core member functions. There is, however, no need to
|
||||||
|
standardize the gateway protocol. Note that even if
|
||||||
|
``iterator_core_access`` used public member functions it would not
|
||||||
|
open a safety loophole, as every core member function preserves the
|
||||||
|
invariants of the iterator.
|
||||||
|
|
||||||
|
``operator[]``
|
||||||
|
--------------
|
||||||
|
|
||||||
|
The indexing operator for a generalized iterator presents special
|
||||||
|
challenges. A random access iterator's ``operator[]`` is only
|
||||||
|
required to return something convertible to its ``value_type``.
|
||||||
|
Requiring that it return an lvalue would rule out currently-legal
|
||||||
|
random-access iterators which hold the referenced value in a data
|
||||||
|
member (e.g. |counting|_), because ``*(p+n)`` is a reference
|
||||||
|
into the temporary iterator ``p+n``, which is destroyed when
|
||||||
|
``operator[]`` returns.
|
||||||
|
|
||||||
|
.. |counting| replace:: ``counting_iterator``
|
||||||
|
|
||||||
|
Writable iterators built with ``iterator_facade`` implement the
|
||||||
|
semantics required by the preferred resolution to `issue 299`_ and
|
||||||
|
adopted by proposal n1550_: the result of ``p[n]`` is an object
|
||||||
|
convertible to the iterator's ``value_type``, and ``p[n] = x`` is
|
||||||
|
equivalent to ``*(p + n) = x`` (Note: This result object may be
|
||||||
|
implemented as a proxy containing a copy of ``p+n``). This approach
|
||||||
|
will work properly for any random-access iterator regardless of the
|
||||||
|
other details of its implementation. A user who knows more about
|
||||||
|
the implementation of her iterator is free to implement an
|
||||||
|
``operator[]`` that returns an lvalue in the derived iterator
|
||||||
|
class; it will hide the one supplied by ``iterator_facade`` from
|
||||||
|
clients of her iterator.
|
||||||
|
|
||||||
|
.. _n1550: http://anubis.dkuug.dk/JTC1/SC22/WG21/docs/papers/2003/n1550.html
|
||||||
|
|
||||||
|
.. _`issue 299`: http://anubis.dkuug.dk/jtc1/sc22/wg21/docs/lwg-active.html#299
|
||||||
|
|
||||||
|
.. _`operator arrow`:
|
||||||
|
|
||||||
|
|
||||||
|
``operator->``
|
||||||
|
--------------
|
||||||
|
|
||||||
|
The ``reference`` type of a readable iterator (and today's input
|
||||||
|
iterator) need not in fact be a reference, so long as it is
|
||||||
|
convertible to the iterator's ``value_type``. When the ``value_type``
|
||||||
|
is a class, however, it must still be possible to access members
|
||||||
|
through ``operator->``. Therefore, an iterator whose ``reference``
|
||||||
|
type is not in fact a reference must return a proxy containing a copy
|
||||||
|
of the referenced value from its ``operator->``.
|
||||||
|
|
||||||
|
The return types for ``iterator_facade``\ 's ``operator->`` and
|
||||||
|
``operator[]`` are not explicitly specified. Instead, those types
|
||||||
|
are described in terms of a set of requirements, which must be
|
||||||
|
satisfied by the ``iterator_facade`` implementation.
|
||||||
|
|
||||||
|
.. [Cop95] [Coplien, 1995] Coplien, J., Curiously Recurring Template
|
||||||
|
Patterns, C++ Report, February 1995, pp. 24-27.
|
||||||
|
|
441
doc/iterator_facade_ref.rst
Normal file
441
doc/iterator_facade_ref.rst
Normal file
@ -0,0 +1,441 @@
|
|||||||
|
.. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
.. Version 1.3 of this ReStructuredText document corresponds to
|
||||||
|
n1530_, the paper accepted by the LWG for TR1.
|
||||||
|
|
||||||
|
.. Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003.
|
||||||
|
|
||||||
|
|
||||||
|
.. parsed-literal::
|
||||||
|
|
||||||
|
template <
|
||||||
|
class Derived
|
||||||
|
, class Value
|
||||||
|
, class CategoryOrTraversal
|
||||||
|
, class Reference = Value&
|
||||||
|
, class Difference = ptrdiff_t
|
||||||
|
>
|
||||||
|
class iterator_facade {
|
||||||
|
public:
|
||||||
|
typedef remove_const<Value>::type value_type;
|
||||||
|
typedef Reference reference;
|
||||||
|
typedef Value\* pointer;
|
||||||
|
typedef Difference difference_type;
|
||||||
|
typedef /* see below__ \*/ iterator_category;
|
||||||
|
|
||||||
|
reference operator\*() const;
|
||||||
|
/* see below__ \*/ operator->() const;
|
||||||
|
/* see below__ \*/ operator[](difference_type n) const;
|
||||||
|
Derived& operator++();
|
||||||
|
Derived operator++(int);
|
||||||
|
Derived& operator--();
|
||||||
|
Derived operator--(int);
|
||||||
|
Derived& operator+=(difference_type n);
|
||||||
|
Derived& operator-=(difference_type n);
|
||||||
|
Derived operator-(difference_type n) const;
|
||||||
|
protected:
|
||||||
|
typedef iterator_facade iterator_facade\_;
|
||||||
|
};
|
||||||
|
|
||||||
|
// Comparison operators
|
||||||
|
template <class Dr1, class V1, class TC1, class R1, class D1,
|
||||||
|
class Dr2, class V2, class TC2, class R2, class D2>
|
||||||
|
typename enable_if_interoperable<Dr1,Dr2,bool>::type // exposition
|
||||||
|
operator ==(iterator_facade<Dr1,V1,TC1,R1,D1> const& lhs,
|
||||||
|
iterator_facade<Dr2,V2,TC2,R2,D2> const& rhs);
|
||||||
|
|
||||||
|
template <class Dr1, class V1, class TC1, class R1, class D1,
|
||||||
|
class Dr2, class V2, class TC2, class R2, class D2>
|
||||||
|
typename enable_if_interoperable<Dr1,Dr2,bool>::type
|
||||||
|
operator !=(iterator_facade<Dr1,V1,TC1,R1,D1> const& lhs,
|
||||||
|
iterator_facade<Dr2,V2,TC2,R2,D2> const& rhs);
|
||||||
|
|
||||||
|
template <class Dr1, class V1, class TC1, class R1, class D1,
|
||||||
|
class Dr2, class V2, class TC2, class R2, class D2>
|
||||||
|
typename enable_if_interoperable<Dr1,Dr2,bool>::type
|
||||||
|
operator <(iterator_facade<Dr1,V1,TC1,R1,D1> const& lhs,
|
||||||
|
iterator_facade<Dr2,V2,TC2,R2,D2> const& rhs);
|
||||||
|
|
||||||
|
template <class Dr1, class V1, class TC1, class R1, class D1,
|
||||||
|
class Dr2, class V2, class TC2, class R2, class D2>
|
||||||
|
typename enable_if_interoperable<Dr1,Dr2,bool>::type
|
||||||
|
operator <=(iterator_facade<Dr1,V1,TC1,R1,D1> const& lhs,
|
||||||
|
iterator_facade<Dr2,V2,TC2,R2,D2> const& rhs);
|
||||||
|
|
||||||
|
template <class Dr1, class V1, class TC1, class R1, class D1,
|
||||||
|
class Dr2, class V2, class TC2, class R2, class D2>
|
||||||
|
typename enable_if_interoperable<Dr1,Dr2,bool>::type
|
||||||
|
operator >(iterator_facade<Dr1,V1,TC1,R1,D1> const& lhs,
|
||||||
|
iterator_facade<Dr2,V2,TC2,R2,D2> const& rhs);
|
||||||
|
|
||||||
|
template <class Dr1, class V1, class TC1, class R1, class D1,
|
||||||
|
class Dr2, class V2, class TC2, class R2, class D2>
|
||||||
|
typename enable_if_interoperable<Dr1,Dr2,bool>::type
|
||||||
|
operator >=(iterator_facade<Dr1,V1,TC1,R1,D1> const& lhs,
|
||||||
|
iterator_facade<Dr2,V2,TC2,R2,D2> const& rhs);
|
||||||
|
|
||||||
|
// Iterator difference
|
||||||
|
template <class Dr1, class V1, class TC1, class R1, class D1,
|
||||||
|
class Dr2, class V2, class TC2, class R2, class D2>
|
||||||
|
/* see below__ \*/
|
||||||
|
operator-(iterator_facade<Dr1,V1,TC1,R1,D1> const& lhs,
|
||||||
|
iterator_facade<Dr2,V2,TC2,R2,D2> const& rhs);
|
||||||
|
|
||||||
|
// Iterator addition
|
||||||
|
template <class Dr, class V, class TC, class R, class D>
|
||||||
|
Derived operator+ (iterator_facade<Dr,V,TC,R,D> const&,
|
||||||
|
typename Derived::difference_type n);
|
||||||
|
|
||||||
|
template <class Dr, class V, class TC, class R, class D>
|
||||||
|
Derived operator+ (typename Derived::difference_type n,
|
||||||
|
iterator_facade<Dr,V,TC,R,D> const&);
|
||||||
|
|
||||||
|
__ `iterator category`_
|
||||||
|
|
||||||
|
__ `operator arrow`_
|
||||||
|
|
||||||
|
__ brackets_
|
||||||
|
|
||||||
|
__ minus_
|
||||||
|
|
||||||
|
.. _`iterator category`:
|
||||||
|
|
||||||
|
The ``iterator_category`` member of ``iterator_facade`` is
|
||||||
|
|
||||||
|
.. parsed-literal::
|
||||||
|
|
||||||
|
*iterator-category*\ (CategoryOrTraversal, value_type, reference)
|
||||||
|
|
||||||
|
where *iterator-category* is defined as follows:
|
||||||
|
|
||||||
|
.. include:: facade_iterator_category.rst
|
||||||
|
|
||||||
|
The ``enable_if_interoperable`` template used above is for exposition
|
||||||
|
purposes. The member operators should only be in an overload set
|
||||||
|
provided the derived types ``Dr1`` and ``Dr2`` are interoperable,
|
||||||
|
meaning that at least one of the types is convertible to the other. The
|
||||||
|
``enable_if_interoperable`` approach uses SFINAE to take the operators
|
||||||
|
out of the overload set when the types are not interoperable.
|
||||||
|
The operators should behave *as-if* ``enable_if_interoperable``
|
||||||
|
were defined to be::
|
||||||
|
|
||||||
|
template <bool, typename> enable_if_interoperable_impl
|
||||||
|
{};
|
||||||
|
|
||||||
|
template <typename T> enable_if_interoperable_impl<true,T>
|
||||||
|
{ typedef T type; };
|
||||||
|
|
||||||
|
template<typename Dr1, typename Dr2, typename T>
|
||||||
|
struct enable_if_interoperable
|
||||||
|
: enable_if_interoperable_impl<
|
||||||
|
is_convertible<Dr1,Dr2>::value || is_convertible<Dr2,Dr1>::value
|
||||||
|
, T
|
||||||
|
>
|
||||||
|
{};
|
||||||
|
|
||||||
|
|
||||||
|
``iterator_facade`` Requirements
|
||||||
|
--------------------------------
|
||||||
|
|
||||||
|
The following table describes the typical valid expressions on
|
||||||
|
``iterator_facade``\ 's ``Derived`` parameter, depending on the
|
||||||
|
iterator concept(s) it will model. The operations in the first
|
||||||
|
column must be made accessible to member functions of class
|
||||||
|
``iterator_core_access``. In addition,
|
||||||
|
``static_cast<Derived*>(iterator_facade*)`` shall be well-formed.
|
||||||
|
|
||||||
|
In the table below, ``F`` is ``iterator_facade<X,V,C,R,D>``, ``a`` is an
|
||||||
|
object of type ``X``, ``b`` and ``c`` are objects of type ``const X``,
|
||||||
|
``n`` is an object of ``F::difference_type``, ``y`` is a constant
|
||||||
|
object of a single pass iterator type interoperable with ``X``, and ``z``
|
||||||
|
is a constant object of a random access traversal iterator type
|
||||||
|
interoperable with ``X``.
|
||||||
|
|
||||||
|
.. _`core operations`:
|
||||||
|
|
||||||
|
.. topic:: ``iterator_facade`` Core Operations
|
||||||
|
|
||||||
|
+--------------------+----------------------+-------------------------+---------------------------+
|
||||||
|
|Expression |Return Type |Assertion/Note |Used to implement Iterator |
|
||||||
|
| | | |Concept(s) |
|
||||||
|
+====================+======================+=========================+===========================+
|
||||||
|
|``c.dereference()`` |``F::reference`` | |Readable Iterator, Writable|
|
||||||
|
| | | |Iterator |
|
||||||
|
+--------------------+----------------------+-------------------------+---------------------------+
|
||||||
|
|``c.equal(y)`` |convertible to bool |true iff ``c`` and ``y`` |Single Pass Iterator |
|
||||||
|
| | |refer to the same | |
|
||||||
|
| | |position. | |
|
||||||
|
+--------------------+----------------------+-------------------------+---------------------------+
|
||||||
|
|``a.increment()`` |unused | |Incrementable Iterator |
|
||||||
|
+--------------------+----------------------+-------------------------+---------------------------+
|
||||||
|
|``a.decrement()`` |unused | |Bidirectional Traversal |
|
||||||
|
| | | |Iterator |
|
||||||
|
+--------------------+----------------------+-------------------------+---------------------------+
|
||||||
|
|``a.advance(n)`` |unused | |Random Access Traversal |
|
||||||
|
| | | |Iterator |
|
||||||
|
+--------------------+----------------------+-------------------------+---------------------------+
|
||||||
|
|``c.distance_to(z)``|convertible to |equivalent to |Random Access Traversal |
|
||||||
|
| |``F::difference_type``|``distance(c, X(z))``. |Iterator |
|
||||||
|
+--------------------+----------------------+-------------------------+---------------------------+
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
``iterator_facade`` operations
|
||||||
|
------------------------------
|
||||||
|
|
||||||
|
The operations in this section are described in terms of operations on
|
||||||
|
the core interface of ``Derived`` which may be inaccessible
|
||||||
|
(i.e. private). The implementation should access these operations
|
||||||
|
through member functions of class ``iterator_core_access``.
|
||||||
|
|
||||||
|
``reference operator*() const;``
|
||||||
|
|
||||||
|
:Returns: ``static_cast<Derived const*>(this)->dereference()``
|
||||||
|
|
||||||
|
``operator->() const;`` (see below__)
|
||||||
|
|
||||||
|
__ `operator arrow`_
|
||||||
|
|
||||||
|
:Returns: If ``reference`` is a reference type, an object
|
||||||
|
of type ``pointer`` equal to::
|
||||||
|
|
||||||
|
&static_cast<Derived const*>(this)->dereference()
|
||||||
|
|
||||||
|
Otherwise returns an object of unspecified type such that,
|
||||||
|
``(*static_cast<Derived const*>(this))->m`` is equivalent to ``(w = **static_cast<Derived const*>(this),
|
||||||
|
w.m)`` for some temporary object ``w`` of type ``value_type``.
|
||||||
|
|
||||||
|
.. _brackets:
|
||||||
|
|
||||||
|
*unspecified* ``operator[](difference_type n) const;``
|
||||||
|
|
||||||
|
:Returns: an object convertible to ``value_type``. For constant
|
||||||
|
objects ``v`` of type ``value_type``, and ``n`` of type
|
||||||
|
``difference_type``, ``(*this)[n] = v`` is equivalent to
|
||||||
|
``*(*this + n) = v``, and ``static_cast<value_type
|
||||||
|
const&>((*this)[n])`` is equivalent to
|
||||||
|
``static_cast<value_type const&>(*(*this + n))``
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
``Derived& operator++();``
|
||||||
|
|
||||||
|
:Effects:
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
static_cast<Derived*>(this)->increment();
|
||||||
|
return *static_cast<Derived*>(this);
|
||||||
|
|
||||||
|
``Derived operator++(int);``
|
||||||
|
|
||||||
|
:Effects:
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
Derived tmp(static_cast<Derived const*>(this));
|
||||||
|
++*this;
|
||||||
|
return tmp;
|
||||||
|
|
||||||
|
|
||||||
|
``Derived& operator--();``
|
||||||
|
|
||||||
|
:Effects:
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
static_cast<Derived*>(this)->decrement();
|
||||||
|
return *static_cast<Derived*>(this);
|
||||||
|
|
||||||
|
|
||||||
|
``Derived operator--(int);``
|
||||||
|
|
||||||
|
:Effects:
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
Derived tmp(static_cast<Derived const*>(this));
|
||||||
|
--*this;
|
||||||
|
return tmp;
|
||||||
|
|
||||||
|
|
||||||
|
``Derived& operator+=(difference_type n);``
|
||||||
|
|
||||||
|
:Effects:
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
static_cast<Derived*>(this)->advance(n);
|
||||||
|
return *static_cast<Derived*>(this);
|
||||||
|
|
||||||
|
|
||||||
|
``Derived& operator-=(difference_type n);``
|
||||||
|
|
||||||
|
:Effects:
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
static_cast<Derived*>(this)->advance(-n);
|
||||||
|
return *static_cast<Derived*>(this);
|
||||||
|
|
||||||
|
|
||||||
|
``Derived operator-(difference_type n) const;``
|
||||||
|
|
||||||
|
:Effects:
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
Derived tmp(static_cast<Derived const*>(this));
|
||||||
|
return tmp -= n;
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <class Dr, class V, class TC, class R, class D>
|
||||||
|
Derived operator+ (iterator_facade<Dr,V,TC,R,D> const&,
|
||||||
|
typename Derived::difference_type n);
|
||||||
|
|
||||||
|
template <class Dr, class V, class TC, class R, class D>
|
||||||
|
Derived operator+ (typename Derived::difference_type n,
|
||||||
|
iterator_facade<Dr,V,TC,R,D> const&);
|
||||||
|
|
||||||
|
:Effects:
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
Derived tmp(static_cast<Derived const*>(this));
|
||||||
|
return tmp += n;
|
||||||
|
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <class Dr1, class V1, class TC1, class R1, class D1,
|
||||||
|
class Dr2, class V2, class TC2, class R2, class D2>
|
||||||
|
typename enable_if_interoperable<Dr1,Dr2,bool>::type
|
||||||
|
operator ==(iterator_facade<Dr1,V1,TC1,R1,D1> const& lhs,
|
||||||
|
iterator_facade<Dr2,V2,TC2,R2,D2> const& rhs);
|
||||||
|
|
||||||
|
:Returns:
|
||||||
|
if ``is_convertible<Dr2,Dr1>::value``
|
||||||
|
|
||||||
|
then
|
||||||
|
``((Dr1 const&)lhs).equal((Dr2 const&)rhs)``.
|
||||||
|
|
||||||
|
Otherwise,
|
||||||
|
``((Dr2 const&)rhs).equal((Dr1 const&)lhs)``.
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <class Dr1, class V1, class TC1, class R1, class D1,
|
||||||
|
class Dr2, class V2, class TC2, class R2, class D2>
|
||||||
|
typename enable_if_interoperable<Dr1,Dr2,bool>::type
|
||||||
|
operator !=(iterator_facade<Dr1,V1,TC1,R1,D1> const& lhs,
|
||||||
|
iterator_facade<Dr2,V2,TC2,R2,D2> const& rhs);
|
||||||
|
|
||||||
|
:Returns:
|
||||||
|
if ``is_convertible<Dr2,Dr1>::value``
|
||||||
|
|
||||||
|
then
|
||||||
|
``!((Dr1 const&)lhs).equal((Dr2 const&)rhs)``.
|
||||||
|
|
||||||
|
Otherwise,
|
||||||
|
``!((Dr2 const&)rhs).equal((Dr1 const&)lhs)``.
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <class Dr1, class V1, class TC1, class R1, class D1,
|
||||||
|
class Dr2, class V2, class TC2, class R2, class D2>
|
||||||
|
typename enable_if_interoperable<Dr1,Dr2,bool>::type
|
||||||
|
operator <(iterator_facade<Dr1,V1,TC1,R1,D1> const& lhs,
|
||||||
|
iterator_facade<Dr2,V2,TC2,R2,D2> const& rhs);
|
||||||
|
|
||||||
|
:Returns:
|
||||||
|
if ``is_convertible<Dr2,Dr1>::value``
|
||||||
|
|
||||||
|
then
|
||||||
|
``((Dr1 const&)lhs).distance_to((Dr2 const&)rhs) < 0``.
|
||||||
|
|
||||||
|
Otherwise,
|
||||||
|
``((Dr2 const&)rhs).distance_to((Dr1 const&)lhs) > 0``.
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <class Dr1, class V1, class TC1, class R1, class D1,
|
||||||
|
class Dr2, class V2, class TC2, class R2, class D2>
|
||||||
|
typename enable_if_interoperable<Dr1,Dr2,bool>::type
|
||||||
|
operator <=(iterator_facade<Dr1,V1,TC1,R1,D1> const& lhs,
|
||||||
|
iterator_facade<Dr2,V2,TC2,R2,D2> const& rhs);
|
||||||
|
|
||||||
|
:Returns:
|
||||||
|
if ``is_convertible<Dr2,Dr1>::value``
|
||||||
|
|
||||||
|
then
|
||||||
|
``((Dr1 const&)lhs).distance_to((Dr2 const&)rhs) <= 0``.
|
||||||
|
|
||||||
|
Otherwise,
|
||||||
|
``((Dr2 const&)rhs).distance_to((Dr1 const&)lhs) >= 0``.
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <class Dr1, class V1, class TC1, class R1, class D1,
|
||||||
|
class Dr2, class V2, class TC2, class R2, class D2>
|
||||||
|
typename enable_if_interoperable<Dr1,Dr2,bool>::type
|
||||||
|
operator >(iterator_facade<Dr1,V1,TC1,R1,D1> const& lhs,
|
||||||
|
iterator_facade<Dr2,V2,TC2,R2,D2> const& rhs);
|
||||||
|
|
||||||
|
:Returns:
|
||||||
|
if ``is_convertible<Dr2,Dr1>::value``
|
||||||
|
|
||||||
|
then
|
||||||
|
``((Dr1 const&)lhs).distance_to((Dr2 const&)rhs) > 0``.
|
||||||
|
|
||||||
|
Otherwise,
|
||||||
|
``((Dr2 const&)rhs).distance_to((Dr1 const&)lhs) < 0``.
|
||||||
|
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <class Dr1, class V1, class TC1, class R1, class D1,
|
||||||
|
class Dr2, class V2, class TC2, class R2, class D2>
|
||||||
|
typename enable_if_interoperable<Dr1,Dr2,bool>::type
|
||||||
|
operator >=(iterator_facade<Dr1,V1,TC1,R1,D1> const& lhs,
|
||||||
|
iterator_facade<Dr2,V2,TC2,R2,D2> const& rhs);
|
||||||
|
|
||||||
|
:Returns:
|
||||||
|
if ``is_convertible<Dr2,Dr1>::value``
|
||||||
|
|
||||||
|
then
|
||||||
|
``((Dr1 const&)lhs).distance_to((Dr2 const&)rhs) >= 0``.
|
||||||
|
|
||||||
|
Otherwise,
|
||||||
|
``((Dr2 const&)rhs).distance_to((Dr1 const&)lhs) <= 0``.
|
||||||
|
|
||||||
|
.. _minus:
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <class Dr1, class V1, class TC1, class R1, class D1,
|
||||||
|
class Dr2, class V2, class TC2, class R2, class D2>
|
||||||
|
typename enable_if_interoperable<Dr1,Dr2,difference>::type
|
||||||
|
operator -(iterator_facade<Dr1,V1,TC1,R1,D1> const& lhs,
|
||||||
|
iterator_facade<Dr2,V2,TC2,R2,D2> const& rhs);
|
||||||
|
|
||||||
|
:Return Type:
|
||||||
|
if ``is_convertible<Dr2,Dr1>::value``
|
||||||
|
|
||||||
|
then
|
||||||
|
``difference`` shall be
|
||||||
|
``iterator_traits<Dr1>::difference_type``.
|
||||||
|
|
||||||
|
Otherwise
|
||||||
|
``difference`` shall be ``iterator_traits<Dr2>::difference_type``
|
||||||
|
|
||||||
|
:Returns:
|
||||||
|
if ``is_convertible<Dr2,Dr1>::value``
|
||||||
|
|
||||||
|
then
|
||||||
|
``-((Dr1 const&)lhs).distance_to((Dr2 const&)rhs)``.
|
||||||
|
|
||||||
|
Otherwise,
|
||||||
|
``((Dr2 const&)rhs).distance_to((Dr1 const&)lhs)``.
|
523
doc/iterator_facade_tutorial.rst
Normal file
523
doc/iterator_facade_tutorial.rst
Normal file
@ -0,0 +1,523 @@
|
|||||||
|
.. Copyright David Abrahams 2004. Use, modification and distribution is
|
||||||
|
.. subject to the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
In this section we'll walk through the implementation of a few
|
||||||
|
iterators using ``iterator_facade``, based around the simple
|
||||||
|
example of a linked list of polymorphic objects. This example was
|
||||||
|
inspired by a `posting`__ by Keith Macdonald on the `Boost-Users`_
|
||||||
|
mailing list.
|
||||||
|
|
||||||
|
.. _`Boost-Users`: http://www.boost.org/more/mailing_lists.htm#users
|
||||||
|
|
||||||
|
__ http://thread.gmane.org/gmane.comp.lib.boost.user/5100
|
||||||
|
|
||||||
|
The Problem
|
||||||
|
-----------
|
||||||
|
|
||||||
|
Say we've written a polymorphic linked list node base class::
|
||||||
|
|
||||||
|
# include <iostream>
|
||||||
|
|
||||||
|
struct node_base
|
||||||
|
{
|
||||||
|
node_base() : m_next(0) {}
|
||||||
|
|
||||||
|
// Each node manages all of its tail nodes
|
||||||
|
virtual ~node_base() { delete m_next; }
|
||||||
|
|
||||||
|
// Access the rest of the list
|
||||||
|
node_base* next() const { return m_next; }
|
||||||
|
|
||||||
|
// print to the stream
|
||||||
|
virtual void print(std::ostream& s) const = 0;
|
||||||
|
|
||||||
|
// double the value
|
||||||
|
virtual void double_me() = 0;
|
||||||
|
|
||||||
|
void append(node_base* p)
|
||||||
|
{
|
||||||
|
if (m_next)
|
||||||
|
m_next->append(p);
|
||||||
|
else
|
||||||
|
m_next = p;
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
node_base* m_next;
|
||||||
|
};
|
||||||
|
|
||||||
|
Lists can hold objects of different types by linking together
|
||||||
|
specializations of the following template::
|
||||||
|
|
||||||
|
template <class T>
|
||||||
|
struct node : node_base
|
||||||
|
{
|
||||||
|
node(T x)
|
||||||
|
: m_value(x)
|
||||||
|
{}
|
||||||
|
|
||||||
|
void print(std::ostream& s) const { s << this->m_value; }
|
||||||
|
void double_me() { m_value += m_value; }
|
||||||
|
|
||||||
|
private:
|
||||||
|
T m_value;
|
||||||
|
};
|
||||||
|
|
||||||
|
And we can print any node using the following streaming operator::
|
||||||
|
|
||||||
|
inline std::ostream& operator<<(std::ostream& s, node_base const& n)
|
||||||
|
{
|
||||||
|
n.print(s);
|
||||||
|
return s;
|
||||||
|
}
|
||||||
|
|
||||||
|
Our first challenge is to build an appropriate iterator over these
|
||||||
|
lists.
|
||||||
|
|
||||||
|
A Basic Iterator Using ``iterator_facade``
|
||||||
|
------------------------------------------
|
||||||
|
|
||||||
|
We will construct a ``node_iterator`` class using inheritance from
|
||||||
|
``iterator_facade`` to implement most of the iterator's operations.
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
# include "node.hpp"
|
||||||
|
# include <boost/iterator/iterator_facade.hpp>
|
||||||
|
|
||||||
|
class node_iterator
|
||||||
|
: public boost::iterator_facade<...>
|
||||||
|
{
|
||||||
|
...
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
Template Arguments for ``iterator_facade``
|
||||||
|
..........................................
|
||||||
|
|
||||||
|
``iterator_facade`` has several template parameters, so we must decide
|
||||||
|
what types to use for the arguments. The parameters are ``Derived``,
|
||||||
|
``Value``, ``CategoryOrTraversal``, ``Reference``, and ``Difference``.
|
||||||
|
|
||||||
|
|
||||||
|
``Derived``
|
||||||
|
'''''''''''
|
||||||
|
|
||||||
|
Because ``iterator_facade`` is meant to be used with the CRTP
|
||||||
|
[Cop95]_ the first parameter is the iterator class name itself,
|
||||||
|
``node_iterator``.
|
||||||
|
|
||||||
|
``Value``
|
||||||
|
'''''''''
|
||||||
|
|
||||||
|
The ``Value`` parameter determines the ``node_iterator``\ 's
|
||||||
|
``value_type``. In this case, we are iterating over ``node_base``
|
||||||
|
objects, so ``Value`` will be ``node_base``.
|
||||||
|
|
||||||
|
|
||||||
|
``CategoryOrTraversal``
|
||||||
|
'''''''''''''''''''''''
|
||||||
|
|
||||||
|
Now we have to determine which `iterator traversal concept`_ our
|
||||||
|
``node_iterator`` is going to model. Singly-linked lists only have
|
||||||
|
forward links, so our iterator can't can't be a `bidirectional
|
||||||
|
traversal iterator`_. Our iterator should be able to make multiple
|
||||||
|
passes over the same linked list (unlike, say, an
|
||||||
|
``istream_iterator`` which consumes the stream it traverses), so it
|
||||||
|
must be a `forward traversal iterator`_. Therefore, we'll pass
|
||||||
|
``boost::forward_traversal_tag`` in this position [#category]_.
|
||||||
|
|
||||||
|
.. [#category] ``iterator_facade`` also supports old-style category
|
||||||
|
tags, so we could have passed ``std::forward_iterator_tag`` here;
|
||||||
|
either way, the resulting iterator's ``iterator_category`` will
|
||||||
|
end up being ``std::forward_iterator_tag``.
|
||||||
|
|
||||||
|
``Reference``
|
||||||
|
'''''''''''''
|
||||||
|
|
||||||
|
The ``Reference`` argument becomes the type returned by
|
||||||
|
``node_iterator``\ 's dereference operation, and will also be the
|
||||||
|
same as ``std::iterator_traits<node_iterator>::reference``. The
|
||||||
|
library's default for this parameter is ``Value&``; since
|
||||||
|
``node_base&`` is a good choice for the iterator's ``reference``
|
||||||
|
type, we can omit this argument, or pass ``use_default``.
|
||||||
|
|
||||||
|
``Difference``
|
||||||
|
''''''''''''''
|
||||||
|
|
||||||
|
The ``Difference`` argument determines how the distance between
|
||||||
|
two ``node_iterator``\ s will be measured and will also be the
|
||||||
|
same as ``std::iterator_traits<node_iterator>::difference_type``.
|
||||||
|
The library's default for ``Difference`` is ``std::ptrdiff_t``, an
|
||||||
|
appropriate type for measuring the distance between any two
|
||||||
|
addresses in memory, and one that works for almost any iterator,
|
||||||
|
so we can omit this argument, too.
|
||||||
|
|
||||||
|
The declaration of ``node_iterator`` will therefore look something
|
||||||
|
like::
|
||||||
|
|
||||||
|
# include "node.hpp"
|
||||||
|
# include <boost/iterator/iterator_facade.hpp>
|
||||||
|
|
||||||
|
class node_iterator
|
||||||
|
: public boost::iterator_facade<
|
||||||
|
node_iterator
|
||||||
|
, node_base
|
||||||
|
, boost::forward_traversal_tag
|
||||||
|
>
|
||||||
|
{
|
||||||
|
...
|
||||||
|
};
|
||||||
|
|
||||||
|
Constructors and Data Members
|
||||||
|
.............................
|
||||||
|
|
||||||
|
Next we need to decide how to represent the iterator's position.
|
||||||
|
This representation will take the form of data members, so we'll
|
||||||
|
also need to write constructors to initialize them. The
|
||||||
|
``node_iterator``\ 's position is quite naturally represented using
|
||||||
|
a pointer to a ``node_base``. We'll need a constructor to build an
|
||||||
|
iterator from a ``node_base*``, and a default constructor to
|
||||||
|
satisfy the `forward traversal iterator`_ requirements [#default]_.
|
||||||
|
Our ``node_iterator`` then becomes::
|
||||||
|
|
||||||
|
# include "node.hpp"
|
||||||
|
# include <boost/iterator/iterator_facade.hpp>
|
||||||
|
|
||||||
|
class node_iterator
|
||||||
|
: public boost::iterator_facade<
|
||||||
|
node_iterator
|
||||||
|
, node_base
|
||||||
|
, boost::forward_traversal_tag
|
||||||
|
>
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
node_iterator()
|
||||||
|
: m_node(0)
|
||||||
|
{}
|
||||||
|
|
||||||
|
explicit node_iterator(node_base* p)
|
||||||
|
: m_node(p)
|
||||||
|
{}
|
||||||
|
|
||||||
|
private:
|
||||||
|
...
|
||||||
|
node_base* m_node;
|
||||||
|
};
|
||||||
|
|
||||||
|
.. [#default] Technically, the C++ standard places almost no
|
||||||
|
requirements on a default-constructed iterator, so if we were
|
||||||
|
really concerned with efficiency, we could've written the
|
||||||
|
default constructor to leave ``m_node`` uninitialized.
|
||||||
|
|
||||||
|
Implementing the Core Operations
|
||||||
|
................................
|
||||||
|
|
||||||
|
The last step is to implement the `core operations`_ required by
|
||||||
|
the concepts we want our iterator to model. Referring to the
|
||||||
|
table__, we can see that the first three rows are applicable
|
||||||
|
because ``node_iterator`` needs to satisfy the requirements for
|
||||||
|
`readable iterator`_, `single pass iterator`_, and `incrementable
|
||||||
|
iterator`_.
|
||||||
|
|
||||||
|
__ `core operations`_
|
||||||
|
|
||||||
|
We therefore need to supply ``dereference``,
|
||||||
|
``equal``, and ``increment`` members. We don't want these members
|
||||||
|
to become part of ``node_iterator``\ 's public interface, so we can
|
||||||
|
make them private and grant friendship to
|
||||||
|
``boost::iterator_core_access``, a "back-door" that
|
||||||
|
``iterator_facade`` uses to get access to the core operations::
|
||||||
|
|
||||||
|
# include "node.hpp"
|
||||||
|
# include <boost/iterator/iterator_facade.hpp>
|
||||||
|
|
||||||
|
class node_iterator
|
||||||
|
: public boost::iterator_facade<
|
||||||
|
node_iterator
|
||||||
|
, node_base
|
||||||
|
, boost::forward_traversal_tag
|
||||||
|
>
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
node_iterator()
|
||||||
|
: m_node(0) {}
|
||||||
|
|
||||||
|
explicit node_iterator(node_base* p)
|
||||||
|
: m_node(p) {}
|
||||||
|
|
||||||
|
private:
|
||||||
|
friend class boost::iterator_core_access;
|
||||||
|
|
||||||
|
void increment() { m_node = m_node->next(); }
|
||||||
|
|
||||||
|
bool equal(node_iterator const& other) const
|
||||||
|
{
|
||||||
|
return this->m_node == other.m_node;
|
||||||
|
}
|
||||||
|
|
||||||
|
node_base& dereference() const { return *m_node; }
|
||||||
|
|
||||||
|
node_base* m_node;
|
||||||
|
};
|
||||||
|
|
||||||
|
Voil<EFBFBD>; a complete and conforming readable, forward-traversal
|
||||||
|
iterator! For a working example of its use, see `this program`__.
|
||||||
|
|
||||||
|
__ ../example/node_iterator1.cpp
|
||||||
|
|
||||||
|
A constant ``node_iterator``
|
||||||
|
----------------------------
|
||||||
|
|
||||||
|
.. Sidebar:: Constant and Mutable iterators
|
||||||
|
|
||||||
|
The term **mutable iterator** means an iterator through which
|
||||||
|
the object it references (its "referent") can be modified. A
|
||||||
|
**constant iterator** is one which doesn't allow modification of
|
||||||
|
its referent.
|
||||||
|
|
||||||
|
The words *constant* and *mutable* don't refer to the ability to
|
||||||
|
modify the iterator itself. For example, an ``int const*`` is a
|
||||||
|
non-\ ``const`` *constant iterator*, which can be incremented
|
||||||
|
but doesn't allow modification of its referent, and ``int*
|
||||||
|
const`` is a ``const`` *mutable iterator*, which cannot be
|
||||||
|
modified but which allows modification of its referent.
|
||||||
|
|
||||||
|
Confusing? We agree, but those are the standard terms. It
|
||||||
|
probably doesn't help much that a container's constant iterator
|
||||||
|
is called ``const_iterator``.
|
||||||
|
|
||||||
|
Now, our ``node_iterator`` gives clients access to both ``node``\
|
||||||
|
's ``print(std::ostream&) const`` member function, but also its
|
||||||
|
mutating ``double_me()`` member. If we wanted to build a
|
||||||
|
*constant* ``node_iterator``, we'd only have to make three
|
||||||
|
changes:
|
||||||
|
|
||||||
|
.. parsed-literal::
|
||||||
|
|
||||||
|
class const_node_iterator
|
||||||
|
: public boost::iterator_facade<
|
||||||
|
const_node_iterator
|
||||||
|
, node_base **const**
|
||||||
|
, boost::forward_traversal_tag
|
||||||
|
>
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
const_node_iterator()
|
||||||
|
: m_node(0) {}
|
||||||
|
|
||||||
|
explicit const_node_iterator(node_base* p)
|
||||||
|
: m_node(p) {}
|
||||||
|
|
||||||
|
private:
|
||||||
|
friend class boost::iterator_core_access;
|
||||||
|
|
||||||
|
void increment() { m_node = m_node->next(); }
|
||||||
|
|
||||||
|
bool equal(const_node_iterator const& other) const
|
||||||
|
{
|
||||||
|
return this->m_node == other.m_node;
|
||||||
|
}
|
||||||
|
|
||||||
|
node_base **const**\ & dereference() const { return \*m_node; }
|
||||||
|
|
||||||
|
node_base **const**\ * m_node;
|
||||||
|
};
|
||||||
|
|
||||||
|
.. Sidebar:: ``const`` and an iterator's ``value_type``
|
||||||
|
|
||||||
|
The C++ standard requires an iterator's ``value_type`` *not* be
|
||||||
|
``const``\ -qualified, so ``iterator_facade`` strips the
|
||||||
|
``const`` from its ``Value`` parameter in order to produce the
|
||||||
|
iterator's ``value_type``. Making the ``Value`` argument
|
||||||
|
``const`` provides a useful hint to ``iterator_facade`` that the
|
||||||
|
iterator is a *constant iterator*, and the default ``Reference``
|
||||||
|
argument will be correct for all lvalue iterators.
|
||||||
|
|
||||||
|
As a matter of fact, ``node_iterator`` and ``const_node_iterator``
|
||||||
|
are so similar that it makes sense to factor the common code out
|
||||||
|
into a template as follows::
|
||||||
|
|
||||||
|
template <class Value>
|
||||||
|
class node_iter
|
||||||
|
: public boost::iterator_facade<
|
||||||
|
node_iter<Value>
|
||||||
|
, Value
|
||||||
|
, boost::forward_traversal_tag
|
||||||
|
>
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
node_iter()
|
||||||
|
: m_node(0) {}
|
||||||
|
|
||||||
|
explicit node_iter(Value* p)
|
||||||
|
: m_node(p) {}
|
||||||
|
|
||||||
|
private:
|
||||||
|
friend class boost::iterator_core_access;
|
||||||
|
|
||||||
|
bool equal(node_iter<Value> const& other) const
|
||||||
|
{
|
||||||
|
return this->m_node == other.m_node;
|
||||||
|
}
|
||||||
|
|
||||||
|
void increment()
|
||||||
|
{ m_node = m_node->next(); }
|
||||||
|
|
||||||
|
Value& dereference() const
|
||||||
|
{ return *m_node; }
|
||||||
|
|
||||||
|
Value* m_node;
|
||||||
|
};
|
||||||
|
typedef node_iter<node_base> node_iterator;
|
||||||
|
typedef node_iter<node_base const> node_const_iterator;
|
||||||
|
|
||||||
|
|
||||||
|
Interoperability
|
||||||
|
----------------
|
||||||
|
|
||||||
|
Our ``const_node_iterator`` works perfectly well on its own, but
|
||||||
|
taken together with ``node_iterator`` it doesn't quite meet
|
||||||
|
expectations. For example, we'd like to be able to pass a
|
||||||
|
``node_iterator`` where a ``node_const_iterator`` was expected,
|
||||||
|
just as you can with ``std::list<int>``\ 's ``iterator`` and
|
||||||
|
``const_iterator``. Furthermore, given a ``node_iterator`` and a
|
||||||
|
``node_const_iterator`` into the same list, we should be able to
|
||||||
|
compare them for equality.
|
||||||
|
|
||||||
|
This expected ability to use two different iterator types together
|
||||||
|
is known as |interoperability|_. Achieving interoperability in
|
||||||
|
our case is as simple as templatizing the ``equal`` function and
|
||||||
|
adding a templatized converting constructor [#broken]_ [#random]_::
|
||||||
|
|
||||||
|
template <class Value>
|
||||||
|
class node_iter
|
||||||
|
: public boost::iterator_facade<
|
||||||
|
node_iter<Value>
|
||||||
|
, Value
|
||||||
|
, boost::forward_traversal_tag
|
||||||
|
>
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
node_iter()
|
||||||
|
: m_node(0) {}
|
||||||
|
|
||||||
|
explicit node_iter(Value* p)
|
||||||
|
: m_node(p) {}
|
||||||
|
|
||||||
|
template <class OtherValue>
|
||||||
|
node_iter(node_iter<OtherValue> const& other)
|
||||||
|
: m_node(other.m_node) {}
|
||||||
|
|
||||||
|
private:
|
||||||
|
friend class boost::iterator_core_access;
|
||||||
|
template <class> friend class node_iter;
|
||||||
|
|
||||||
|
template <class OtherValue>
|
||||||
|
bool equal(node_iter<OtherValue> const& other) const
|
||||||
|
{
|
||||||
|
return this->m_node == other.m_node;
|
||||||
|
}
|
||||||
|
|
||||||
|
void increment()
|
||||||
|
{ m_node = m_node->next(); }
|
||||||
|
|
||||||
|
Value& dereference() const
|
||||||
|
{ return *m_node; }
|
||||||
|
|
||||||
|
Value* m_node;
|
||||||
|
};
|
||||||
|
typedef impl::node_iterator<node_base> node_iterator;
|
||||||
|
typedef impl::node_iterator<node_base const> node_const_iterator;
|
||||||
|
|
||||||
|
.. |interoperability| replace:: **interoperability**
|
||||||
|
.. _interoperability: new-iter-concepts.html#interoperable-iterators-lib-interoperable-iterators
|
||||||
|
|
||||||
|
.. [#broken] If you're using an older compiler and it can't handle
|
||||||
|
this example, see the `example code`__ for workarounds.
|
||||||
|
|
||||||
|
.. [#random] If ``node_iterator`` had been a `random access
|
||||||
|
traversal iterator`_, we'd have had to templatize its
|
||||||
|
``distance_to`` function as well.
|
||||||
|
|
||||||
|
|
||||||
|
__ ../example/node_iterator2.hpp
|
||||||
|
|
||||||
|
You can see an example program which exercises our interoperable
|
||||||
|
iterators `here`__.
|
||||||
|
|
||||||
|
__ ../example/node_iterator2.cpp
|
||||||
|
|
||||||
|
Telling the Truth
|
||||||
|
-----------------
|
||||||
|
|
||||||
|
Now ``node_iterator`` and ``node_const_iterator`` behave exactly as
|
||||||
|
you'd expect... almost. We can compare them and we can convert in
|
||||||
|
one direction: from ``node_iterator`` to ``node_const_iterator``.
|
||||||
|
If we try to convert from ``node_const_iterator`` to
|
||||||
|
``node_iterator``, we'll get an error when the converting
|
||||||
|
constructor tries to initialize ``node_iterator``\ 's ``m_node``, a
|
||||||
|
``node*`` with a ``node const*``. So what's the problem?
|
||||||
|
|
||||||
|
The problem is that
|
||||||
|
``boost::``\ |is_convertible|_\ ``<node_const_iterator,node_iterator>::value``
|
||||||
|
will be ``true``, but it should be ``false``. |is_convertible|_
|
||||||
|
lies because it can only see as far as the *declaration* of
|
||||||
|
``node_iter``\ 's converting constructor, but can't look inside at
|
||||||
|
the *definition* to make sure it will compile. A perfect solution
|
||||||
|
would make ``node_iter``\ 's converting constructor disappear when
|
||||||
|
the ``m_node`` conversion would fail.
|
||||||
|
|
||||||
|
.. |is_convertible| replace:: ``is_convertible``
|
||||||
|
.. _is_convertible: ../../type_traits/index.html#relationships
|
||||||
|
|
||||||
|
In fact, that sort of magic is possible using
|
||||||
|
|enable_if|__. By rewriting the converting constructor as
|
||||||
|
follows, we can remove it from the overload set when it's not
|
||||||
|
appropriate::
|
||||||
|
|
||||||
|
#include <boost/type_traits/is_convertible.hpp>
|
||||||
|
#include <boost/utility/enable_if.hpp>
|
||||||
|
|
||||||
|
...
|
||||||
|
|
||||||
|
private:
|
||||||
|
struct enabler {};
|
||||||
|
|
||||||
|
public:
|
||||||
|
template <class OtherValue>
|
||||||
|
node_iter(
|
||||||
|
node_iter<OtherValue> const& other
|
||||||
|
, typename boost::enable_if<
|
||||||
|
boost::is_convertible<OtherValue*,Value*>
|
||||||
|
, enabler
|
||||||
|
>::type = enabler()
|
||||||
|
)
|
||||||
|
: m_node(other.m_node) {}
|
||||||
|
|
||||||
|
.. |enable_if| replace:: ``boost::enable_if``
|
||||||
|
__ ../../utility/enable_if.html
|
||||||
|
|
||||||
|
|
||||||
|
Wrap Up
|
||||||
|
-------
|
||||||
|
|
||||||
|
This concludes our ``iterator_facade`` tutorial, but before you
|
||||||
|
stop reading we urge you to take a look at |iterator_adaptor|__.
|
||||||
|
There's another way to approach writing these iterators which might
|
||||||
|
even be superior.
|
||||||
|
|
||||||
|
.. |iterator_adaptor| replace:: ``iterator_adaptor``
|
||||||
|
__ iterator_adaptor.html
|
||||||
|
|
||||||
|
.. _`iterator traversal concept`: new-iter-concepts.html#iterator-traversal-concepts-lib-iterator-traversal
|
||||||
|
.. _`readable iterator`: new-iter-concepts.html#readable-iterators-lib-readable-iterators
|
||||||
|
.. _`lvalue iterator`: new-iter-concepts.html#lvalue-iterators-lib-lvalue-iterators
|
||||||
|
.. _`single pass iterator`: new-iter-concepts.html#single-pass-iterators-lib-single-pass-iterators
|
||||||
|
.. _`incrementable iterator`: new-iter-concepts.html#incrementable-iterators-lib-incrementable-iterators
|
||||||
|
.. _`forward traversal iterator`: new-iter-concepts.html#forward-traversal-iterators-lib-forward-traversal-iterators
|
||||||
|
.. _`bidirectional traversal iterator`: new-iter-concepts.html#bidirectional-traversal-iterators-lib-bidirectional-traversal-iterators
|
||||||
|
.. _`random access traversal iterator`: new-iter-concepts.html#random-access-traversal-iterators-lib-random-access-traversal-iterators
|
||||||
|
|
124
doc/iterator_traits.html
Normal file
124
doc/iterator_traits.html
Normal file
@ -0,0 +1,124 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" />
|
||||||
|
<title>Iterator Traits</title>
|
||||||
|
<meta name="author" content="David Abrahams" />
|
||||||
|
<meta name="organization" content="Boost Consulting" />
|
||||||
|
<meta name="date" content="2006-09-11" />
|
||||||
|
<meta name="copyright" content="Copyright David Abrahams 2004." />
|
||||||
|
<link rel="stylesheet" href="../../../rst.css" type="text/css" />
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="iterator-traits">
|
||||||
|
<h1 class="title">Iterator Traits</h1>
|
||||||
|
<table class="docinfo" frame="void" rules="none">
|
||||||
|
<col class="docinfo-name" />
|
||||||
|
<col class="docinfo-content" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><th class="docinfo-name">Author:</th>
|
||||||
|
<td>David Abrahams</td></tr>
|
||||||
|
<tr><th class="docinfo-name">Contact:</th>
|
||||||
|
<td><a class="first last reference external" href="mailto:dave@boost-consulting.com">dave@boost-consulting.com</a></td></tr>
|
||||||
|
<tr><th class="docinfo-name">Organization:</th>
|
||||||
|
<td><a class="first last reference external" href="http://www.boost-consulting.com">Boost Consulting</a></td></tr>
|
||||||
|
<tr><th class="docinfo-name">Date:</th>
|
||||||
|
<td>2006-09-11</td></tr>
|
||||||
|
<tr><th class="docinfo-name">Copyright:</th>
|
||||||
|
<td>Copyright David Abrahams 2004.</td></tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<!-- Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">abstract:</th><td class="field-body">Header <tt class="docutils literal"><span class="pre"><boost/iterator/iterator_traits.hpp></span></tt> provides
|
||||||
|
the ability to access an iterator's associated types using
|
||||||
|
MPL-compatible <a class="reference external" href="../../mpl/doc/index.html#metafunctions">metafunctions</a>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<div class="section" id="overview">
|
||||||
|
<h1>Overview</h1>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">std::iterator_traits</span></tt> provides access to five associated types
|
||||||
|
of any iterator: its <tt class="docutils literal"><span class="pre">value_type</span></tt>, <tt class="docutils literal"><span class="pre">reference</span></tt>, <tt class="docutils literal"><span class="pre">pointer</span></tt>,
|
||||||
|
<tt class="docutils literal"><span class="pre">iterator_category</span></tt>, and <tt class="docutils literal"><span class="pre">difference_type</span></tt>. Unfortunately,
|
||||||
|
such a "multi-valued" traits template can be difficult to use in a
|
||||||
|
metaprogramming context. <tt class="docutils literal"><span class="pre"><boost/iterator/iterator_traits.hpp></span></tt>
|
||||||
|
provides access to these types using a standard <a class="reference external" href="../../mpl/doc/index.html#metafunctions">metafunctions</a>.</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="summary">
|
||||||
|
<h1>Summary</h1>
|
||||||
|
<p>Header <tt class="docutils literal"><span class="pre"><boost/iterator/iterator_traits.hpp></span></tt>:</p>
|
||||||
|
<pre class="literal-block">
|
||||||
|
template <class Iterator>
|
||||||
|
struct iterator_value
|
||||||
|
{
|
||||||
|
typedef typename
|
||||||
|
std::iterator_traits<Iterator>::value_type
|
||||||
|
type;
|
||||||
|
};
|
||||||
|
|
||||||
|
template <class Iterator>
|
||||||
|
struct iterator_reference
|
||||||
|
{
|
||||||
|
typedef typename
|
||||||
|
std::iterator_traits<Iterator>::reference
|
||||||
|
type;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
template <class Iterator>
|
||||||
|
struct iterator_pointer
|
||||||
|
{
|
||||||
|
typedef typename
|
||||||
|
std::iterator_traits<Iterator>::pointer
|
||||||
|
type;
|
||||||
|
};
|
||||||
|
|
||||||
|
template <class Iterator>
|
||||||
|
struct iterator_difference
|
||||||
|
{
|
||||||
|
typedef typename
|
||||||
|
detail::iterator_traits<Iterator>::difference_type
|
||||||
|
type;
|
||||||
|
};
|
||||||
|
|
||||||
|
template <class Iterator>
|
||||||
|
struct iterator_category
|
||||||
|
{
|
||||||
|
typedef typename
|
||||||
|
detail::iterator_traits<Iterator>::iterator_category
|
||||||
|
type;
|
||||||
|
};
|
||||||
|
</pre>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="broken-compiler-notes">
|
||||||
|
<h1>Broken Compiler Notes</h1>
|
||||||
|
<p>Because of workarounds in Boost, you may find that these
|
||||||
|
<a class="reference external" href="../../mpl/doc/index.html#metafunctions">metafunctions</a> actually work better than the facilities provided by
|
||||||
|
your compiler's standard library.</p>
|
||||||
|
<p>On compilers that don't support partial specialization, such as
|
||||||
|
Microsoft Visual C++ 6.0 or 7.0, you may need to manually invoke
|
||||||
|
<a class="reference external" href="../../type_traits/index.html#transformations">BOOST_BROKEN_COMPILER_TYPE_TRAITS_SPECIALIZATION</a> on the
|
||||||
|
<tt class="docutils literal"><span class="pre">value_type</span></tt> of pointers that are passed to these metafunctions.</p>
|
||||||
|
<p>Because of bugs in the implementation of GCC-2.9x, the name of
|
||||||
|
<tt class="docutils literal"><span class="pre">iterator_category</span></tt> is changed to <tt class="docutils literal"><span class="pre">iterator_category_</span></tt> on that
|
||||||
|
compiler. A macro, <tt class="docutils literal"><span class="pre">BOOST_ITERATOR_CATEGORY</span></tt>, that expands to
|
||||||
|
either <tt class="docutils literal"><span class="pre">iterator_category</span></tt> or <tt class="docutils literal"><span class="pre">iterator_category_</span></tt>, as
|
||||||
|
appropriate to the platform, is provided for portability.</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<hr class="footer" />
|
||||||
|
<a class="reference external" href="iterator_traits.rst">View document source</a>.
|
||||||
|
Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
BIN
doc/iterator_traits.pdf
Normal file
BIN
doc/iterator_traits.pdf
Normal file
Binary file not shown.
98
doc/iterator_traits.rst
Normal file
98
doc/iterator_traits.rst
Normal file
@ -0,0 +1,98 @@
|
|||||||
|
.. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
+++++++++++++++++
|
||||||
|
Iterator Traits
|
||||||
|
+++++++++++++++++
|
||||||
|
|
||||||
|
:Author: David Abrahams
|
||||||
|
:Contact: dave@boost-consulting.com
|
||||||
|
:organization: `Boost Consulting`_
|
||||||
|
:date: $Date$
|
||||||
|
:copyright: Copyright David Abrahams 2004.
|
||||||
|
|
||||||
|
.. _`Boost Consulting`: http://www.boost-consulting.com
|
||||||
|
|
||||||
|
:abstract: Header ``<boost/iterator/iterator_traits.hpp>`` provides
|
||||||
|
the ability to access an iterator's associated types using
|
||||||
|
MPL-compatible metafunctions_.
|
||||||
|
|
||||||
|
.. _metafunctions: ../../mpl/doc/index.html#metafunctions
|
||||||
|
|
||||||
|
Overview
|
||||||
|
========
|
||||||
|
|
||||||
|
``std::iterator_traits`` provides access to five associated types
|
||||||
|
of any iterator: its ``value_type``, ``reference``, ``pointer``,
|
||||||
|
``iterator_category``, and ``difference_type``. Unfortunately,
|
||||||
|
such a "multi-valued" traits template can be difficult to use in a
|
||||||
|
metaprogramming context. ``<boost/iterator/iterator_traits.hpp>``
|
||||||
|
provides access to these types using a standard metafunctions_.
|
||||||
|
|
||||||
|
Summary
|
||||||
|
=======
|
||||||
|
|
||||||
|
Header ``<boost/iterator/iterator_traits.hpp>``::
|
||||||
|
|
||||||
|
template <class Iterator>
|
||||||
|
struct iterator_value
|
||||||
|
{
|
||||||
|
typedef typename
|
||||||
|
std::iterator_traits<Iterator>::value_type
|
||||||
|
type;
|
||||||
|
};
|
||||||
|
|
||||||
|
template <class Iterator>
|
||||||
|
struct iterator_reference
|
||||||
|
{
|
||||||
|
typedef typename
|
||||||
|
std::iterator_traits<Iterator>::reference
|
||||||
|
type;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
template <class Iterator>
|
||||||
|
struct iterator_pointer
|
||||||
|
{
|
||||||
|
typedef typename
|
||||||
|
std::iterator_traits<Iterator>::pointer
|
||||||
|
type;
|
||||||
|
};
|
||||||
|
|
||||||
|
template <class Iterator>
|
||||||
|
struct iterator_difference
|
||||||
|
{
|
||||||
|
typedef typename
|
||||||
|
detail::iterator_traits<Iterator>::difference_type
|
||||||
|
type;
|
||||||
|
};
|
||||||
|
|
||||||
|
template <class Iterator>
|
||||||
|
struct iterator_category
|
||||||
|
{
|
||||||
|
typedef typename
|
||||||
|
detail::iterator_traits<Iterator>::iterator_category
|
||||||
|
type;
|
||||||
|
};
|
||||||
|
|
||||||
|
Broken Compiler Notes
|
||||||
|
=====================
|
||||||
|
|
||||||
|
Because of workarounds in Boost, you may find that these
|
||||||
|
metafunctions_ actually work better than the facilities provided by
|
||||||
|
your compiler's standard library.
|
||||||
|
|
||||||
|
On compilers that don't support partial specialization, such as
|
||||||
|
Microsoft Visual C++ 6.0 or 7.0, you may need to manually invoke
|
||||||
|
BOOST_BROKEN_COMPILER_TYPE_TRAITS_SPECIALIZATION_ on the
|
||||||
|
``value_type`` of pointers that are passed to these metafunctions.
|
||||||
|
|
||||||
|
Because of bugs in the implementation of GCC-2.9x, the name of
|
||||||
|
``iterator_category`` is changed to ``iterator_category_`` on that
|
||||||
|
compiler. A macro, ``BOOST_ITERATOR_CATEGORY``, that expands to
|
||||||
|
either ``iterator_category`` or ``iterator_category_``, as
|
||||||
|
appropriate to the platform, is provided for portability.
|
||||||
|
|
||||||
|
.. _BOOST_BROKEN_COMPILER_TYPE_TRAITS_SPECIALIZATION: ../../type_traits/index.html#transformations
|
||||||
|
|
12
doc/make_counting_iterator.rst
Normal file
12
doc/make_counting_iterator.rst
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <class Incrementable>
|
||||||
|
counting_iterator<Incrementable> make_counting_iterator(Incrementable x);
|
||||||
|
|
||||||
|
:Returns: An instance of ``counting_iterator<Incrementable>``
|
||||||
|
with ``current`` constructed from ``x``.
|
||||||
|
|
19
doc/make_filter_iterator.rst
Normal file
19
doc/make_filter_iterator.rst
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <class Predicate, class Iterator>
|
||||||
|
filter_iterator<Predicate,Iterator>
|
||||||
|
make_filter_iterator(Predicate f, Iterator x, Iterator end = Iterator());
|
||||||
|
|
||||||
|
:Returns: filter_iterator<Predicate,Iterator>(f, x, end)
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <class Predicate, class Iterator>
|
||||||
|
filter_iterator<Predicate,Iterator>
|
||||||
|
make_filter_iterator(Iterator x, Iterator end = Iterator());
|
||||||
|
|
||||||
|
:Returns: filter_iterator<Predicate,Iterator>(x, end)
|
13
doc/make_reverse_iterator.rst
Normal file
13
doc/make_reverse_iterator.rst
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <class BidirectionalIterator>
|
||||||
|
reverse_iterator<BidirectionalIterator>n
|
||||||
|
make_reverse_iterator(BidirectionalIterator x);
|
||||||
|
|
||||||
|
:Returns: An instance of ``reverse_iterator<BidirectionalIterator>``
|
||||||
|
with a ``current`` constructed from ``x``.
|
||||||
|
|
23
doc/make_transform_iterator.rst
Normal file
23
doc/make_transform_iterator.rst
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <class UnaryFunction, class Iterator>
|
||||||
|
transform_iterator<UnaryFunction, Iterator>
|
||||||
|
make_transform_iterator(Iterator it, UnaryFunction fun);
|
||||||
|
|
||||||
|
:Returns: An instance of ``transform_iterator<UnaryFunction, Iterator>`` with ``m_f``
|
||||||
|
initialized to ``f`` and ``m_iterator`` initialized to ``x``.
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template <class UnaryFunction, class Iterator>
|
||||||
|
transform_iterator<UnaryFunction, Iterator>
|
||||||
|
make_transform_iterator(Iterator it);
|
||||||
|
|
||||||
|
:Returns: An instance of ``transform_iterator<UnaryFunction, Iterator>`` with ``m_f``
|
||||||
|
default constructed and ``m_iterator`` initialized to ``x``.
|
12
doc/make_zip_iterator.rst
Normal file
12
doc/make_zip_iterator.rst
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
template<typename IteratorTuple>
|
||||||
|
zip_iterator<IteratorTuple>
|
||||||
|
make_zip_iterator(IteratorTuple t);
|
||||||
|
|
||||||
|
:Returns: An instance of ``zip_iterator<IteratorTuple>`` with ``m_iterator_tuple``
|
||||||
|
initialized to ``t``.
|
1029
doc/new-iter-concepts.html
Normal file
1029
doc/new-iter-concepts.html
Normal file
File diff suppressed because it is too large
Load Diff
BIN
doc/new-iter-concepts.pdf
Normal file
BIN
doc/new-iter-concepts.pdf
Normal file
Binary file not shown.
803
doc/new-iter-concepts.rst
Normal file
803
doc/new-iter-concepts.rst
Normal file
@ -0,0 +1,803 @@
|
|||||||
|
.. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
++++++++++++++++++++++
|
||||||
|
New Iterator Concepts
|
||||||
|
++++++++++++++++++++++
|
||||||
|
|
||||||
|
.. Version 1.25 of this ReStructuredText document is the same as
|
||||||
|
n1550_, the paper accepted by the LWG.
|
||||||
|
|
||||||
|
:Author: David Abrahams, Jeremy Siek, Thomas Witt
|
||||||
|
:Contact: dave@boost-consulting.com, jsiek@osl.iu.edu, witt@styleadvisor.com
|
||||||
|
:organization: `Boost Consulting`_, Indiana University `Open Systems
|
||||||
|
Lab`_, `Zephyr Associates, Inc.`_
|
||||||
|
:date: $Date$
|
||||||
|
|
||||||
|
:Number: This is a revised version of n1550_\ =03-0133, which was
|
||||||
|
accepted for Technical Report 1 by the C++ standard
|
||||||
|
committee's library working group. This proposal is a
|
||||||
|
revision of paper n1297_, n1477_, and n1531_.
|
||||||
|
|
||||||
|
:copyright: Copyright David Abrahams, Jeremy Siek, and Thomas Witt
|
||||||
|
2003.
|
||||||
|
|
||||||
|
.. _`Boost Consulting`: http://www.boost-consulting.com
|
||||||
|
.. _`Open Systems Lab`: http://www.osl.iu.edu
|
||||||
|
.. _`Zephyr Associates, Inc.`: http://www.styleadvisor.com
|
||||||
|
|
||||||
|
.. _`Institute for Transport Railway Operation and Construction`:
|
||||||
|
http://www.ive.uni-hannover.de
|
||||||
|
|
||||||
|
:Abstract: We propose a new system of iterator concepts that treat
|
||||||
|
access and positioning independently. This allows the
|
||||||
|
concepts to more closely match the requirements
|
||||||
|
of algorithms and provides better categorizations
|
||||||
|
of iterators that are used in practice.
|
||||||
|
|
||||||
|
.. contents:: Table of Contents
|
||||||
|
|
||||||
|
.. _n1297: http://anubis.dkuug.dk/jtc1/sc22/wg21/docs/papers/2001/n1297.html
|
||||||
|
.. _n1477: http://anubis.dkuug.dk/jtc1/sc22/wg21/docs/papers/2003/n1477.html
|
||||||
|
.. _n1531: http://anubis.dkuug.dk/jtc1/sc22/wg21/docs/papers/2003/n1531.html
|
||||||
|
.. _n1550: http://anubis.dkuug.dk/jtc1/sc22/wg21/docs/papers/2003/n1550.html
|
||||||
|
|
||||||
|
============
|
||||||
|
Motivation
|
||||||
|
============
|
||||||
|
|
||||||
|
The standard iterator categories and requirements are flawed because
|
||||||
|
they use a single hierarchy of concepts to address two orthogonal
|
||||||
|
issues: *iterator traversal* and *value access*. As a result, many
|
||||||
|
algorithms with requirements expressed in terms of the iterator
|
||||||
|
categories are too strict. Also, many real-world iterators can not be
|
||||||
|
accurately categorized. A proxy-based iterator with random-access
|
||||||
|
traversal, for example, may only legally have a category of "input
|
||||||
|
iterator", so generic algorithms are unable to take advantage of its
|
||||||
|
random-access capabilities. The current iterator concept hierarchy is
|
||||||
|
geared towards iterator traversal (hence the category names), while
|
||||||
|
requirements that address value access sneak in at various places. The
|
||||||
|
following table gives a summary of the current value access
|
||||||
|
requirements in the iterator categories.
|
||||||
|
|
||||||
|
+------------------------------------------------------------------------------+
|
||||||
|
|Value Access Requirements in Existing Iterator Categories |
|
||||||
|
+========================+=====================================================+
|
||||||
|
|Output Iterator |``*i = a`` |
|
||||||
|
+------------------------+-----------------------------------------------------+
|
||||||
|
|Input Iterator |``*i`` is convertible to ``T`` |
|
||||||
|
+------------------------+-----------------------------------------------------+
|
||||||
|
|Forward Iterator |``*i`` is ``T&`` (or ``const T&`` once `issue 200`_ |
|
||||||
|
| |is resolved) |
|
||||||
|
+------------------------+-----------------------------------------------------+
|
||||||
|
|Random Access Iterator |``i[n]`` is convertible to ``T`` (also ``i[n] = t`` |
|
||||||
|
| |is required for mutable iterators once `issue 299`_ |
|
||||||
|
| |is resolved) |
|
||||||
|
+------------------------+-----------------------------------------------------+
|
||||||
|
|
||||||
|
.. _issue 200: http://anubis.dkuug.dk/JTC1/SC22/WG21/docs/lwg-active.html#200
|
||||||
|
.. _issue 299: http://anubis.dkuug.dk/JTC1/SC22/WG21/docs/lwg-active.html#299
|
||||||
|
|
||||||
|
|
||||||
|
Because iterator traversal and value access are mixed together in a
|
||||||
|
single hierarchy, many useful iterators can not be appropriately
|
||||||
|
categorized. For example, ``vector<bool>::iterator`` is almost a
|
||||||
|
random access iterator, but the return type is not ``bool&`` (see
|
||||||
|
`issue 96`_ and Herb Sutter's paper J16/99-0008 = WG21
|
||||||
|
N1185). Therefore, the iterators of ``vector<bool>`` only meet the
|
||||||
|
requirements of input iterator and output iterator. This is so
|
||||||
|
nonintuitive that the C++ standard contradicts itself on this point.
|
||||||
|
In paragraph 23.2.4/1 it says that a ``vector`` is a sequence that
|
||||||
|
supports random access iterators.
|
||||||
|
|
||||||
|
.. _issue 96: http://anubis.dkuug.dk/JTC1/SC22/WG21/docs/lwg-active.html#96
|
||||||
|
|
||||||
|
Another difficult-to-categorize iterator is the transform iterator, an
|
||||||
|
adaptor which applies a unary function object to the dereferenced
|
||||||
|
value of the some underlying iterator (see `transform_iterator`_).
|
||||||
|
For unary functions such as ``times``, the return type of
|
||||||
|
``operator*`` clearly needs to be the ``result_type`` of the function
|
||||||
|
object, which is typically not a reference. Because random access
|
||||||
|
iterators are required to return lvalues from ``operator*``, if you
|
||||||
|
wrap ``int*`` with a transform iterator, you do not get a random
|
||||||
|
access iterator as might be expected, but an input iterator.
|
||||||
|
|
||||||
|
.. _`transform_iterator`: http://www.boost.org/libs/utility/transform_iterator.htm
|
||||||
|
|
||||||
|
A third example is found in the vertex and edge iterators of the
|
||||||
|
`Boost Graph Library`_. These iterators return vertex and edge
|
||||||
|
descriptors, which are lightweight handles created on-the-fly. They
|
||||||
|
must be returned by-value. As a result, their current standard
|
||||||
|
iterator category is ``input_iterator_tag``, which means that,
|
||||||
|
strictly speaking, you could not use these iterators with algorithms
|
||||||
|
like ``min_element()``. As a temporary solution, the concept
|
||||||
|
`Multi-Pass Input Iterator`_ was introduced to describe the vertex and
|
||||||
|
edge descriptors, but as the design notes for the concept suggest, a
|
||||||
|
better solution is needed.
|
||||||
|
|
||||||
|
.. _Boost Graph Library: http://www.boost.org/libs/graph/doc/table_of_contents.html
|
||||||
|
.. _Multi-Pass Input Iterator: http://www.boost.org/libs/utility/MultiPassInputIterator.html
|
||||||
|
|
||||||
|
In short, there are many useful iterators that do not fit into the
|
||||||
|
current standard iterator categories. As a result, the following bad
|
||||||
|
things happen:
|
||||||
|
|
||||||
|
- Iterators are often mis-categorized.
|
||||||
|
|
||||||
|
- Algorithm requirements are more strict than necessary, because they
|
||||||
|
cannot separate the need for random access or bidirectional
|
||||||
|
traversal from the need for a true reference return type.
|
||||||
|
|
||||||
|
|
||||||
|
========================
|
||||||
|
Impact on the Standard
|
||||||
|
========================
|
||||||
|
|
||||||
|
This proposal for TR1 is a pure extension. Further, the new iterator
|
||||||
|
concepts are backward-compatible with the old iterator requirements,
|
||||||
|
and old iterators are forward-compatible with the new iterator
|
||||||
|
concepts. That is to say, iterators that satisfy the old requirements
|
||||||
|
also satisfy appropriate concepts in the new system, and iterators
|
||||||
|
modeling the new concepts will automatically satisfy the appropriate
|
||||||
|
old requirements.
|
||||||
|
|
||||||
|
.. I think we need to say something about the resolution to allow
|
||||||
|
convertibility to any of the old-style tags as a TR issue (hope it
|
||||||
|
made it). -DWA
|
||||||
|
|
||||||
|
.. Hmm, not sure I understand. Are you talking about whether a
|
||||||
|
standards conforming input iterator is allowed to have
|
||||||
|
a tag that is not input_iterator_tag but that
|
||||||
|
is convertible to input_iterator_tag? -JGS
|
||||||
|
|
||||||
|
Possible (but not proposed) Changes to the Working Paper
|
||||||
|
========================================================
|
||||||
|
|
||||||
|
The extensions in this paper suggest several changes we might make
|
||||||
|
to the working paper for the next standard. These changes are not
|
||||||
|
a formal part of this proposal for TR1.
|
||||||
|
|
||||||
|
Changes to Algorithm Requirements
|
||||||
|
+++++++++++++++++++++++++++++++++
|
||||||
|
|
||||||
|
The algorithms in the standard library could benefit from the new
|
||||||
|
iterator concepts because the new concepts provide a more accurate way
|
||||||
|
to express their type requirements. The result is algorithms that are
|
||||||
|
usable in more situations and have fewer type requirements.
|
||||||
|
|
||||||
|
For the next working paper (but not for TR1), the committee should
|
||||||
|
consider the following changes to the type requirements of algorithms.
|
||||||
|
These changes are phrased as textual substitutions, listing the
|
||||||
|
algorithms to which each textual substitution applies.
|
||||||
|
|
||||||
|
Forward Iterator -> Forward Traversal Iterator and Readable Iterator
|
||||||
|
|
||||||
|
``find_end, adjacent_find, search, search_n, rotate_copy,
|
||||||
|
lower_bound, upper_bound, equal_range, binary_search,
|
||||||
|
min_element, max_element``
|
||||||
|
|
||||||
|
Forward Iterator (1) -> Single Pass Iterator and Readable Iterator,
|
||||||
|
Forward Iterator (2) -> Forward Traversal Iterator and Readable Iterator
|
||||||
|
|
||||||
|
``find_first_of``
|
||||||
|
|
||||||
|
Forward Iterator -> Readable Iterator and Writable Iterator
|
||||||
|
|
||||||
|
``iter_swap``
|
||||||
|
|
||||||
|
Forward Iterator -> Single Pass Iterator and Writable Iterator
|
||||||
|
|
||||||
|
``fill, generate``
|
||||||
|
|
||||||
|
Forward Iterator -> Forward Traversal Iterator and Swappable Iterator
|
||||||
|
|
||||||
|
``rotate``
|
||||||
|
|
||||||
|
Forward Iterator (1) -> Swappable Iterator and Single Pass Iterator,
|
||||||
|
Forward Iterator (2) -> Swappable Iterator and Incrementable Iterator
|
||||||
|
|
||||||
|
``swap_ranges``
|
||||||
|
|
||||||
|
Forward Iterator -> Forward Traversal Iterator and Readable Iterator and Writable Iterator
|
||||||
|
``remove, remove_if, unique``
|
||||||
|
|
||||||
|
Forward Iterator -> Single Pass Iterator and Readable Iterator and Writable Iterator
|
||||||
|
|
||||||
|
``replace, replace_if``
|
||||||
|
|
||||||
|
Bidirectional Iterator -> Bidirectional Traversal Iterator and Swappable Iterator
|
||||||
|
``reverse``
|
||||||
|
|
||||||
|
Bidirectional Iterator -> Bidirectional Traversal Iterator and Readable and Swappable Iterator
|
||||||
|
``partition``
|
||||||
|
|
||||||
|
Bidirectional Iterator (1) -> Bidirectional Traversal Iterator and Readable Iterator,
|
||||||
|
Bidirectional Iterator (2) -> Bidirectional Traversal Iterator and Writable Iterator
|
||||||
|
|
||||||
|
``copy_backwards``
|
||||||
|
|
||||||
|
Bidirectional Iterator -> Bidirectional Traversal Iterator and Swappable Iterator and Readable Iterator
|
||||||
|
``next_permutation, prev_permutation``
|
||||||
|
|
||||||
|
Bidirectional Iterator -> Bidirectional Traversal Iterator and Readable Iterator and Writable Iterator
|
||||||
|
``stable_partition, inplace_merge``
|
||||||
|
|
||||||
|
Bidirectional Iterator -> Bidirectional Traversal Iterator and Readable Iterator
|
||||||
|
``reverse_copy``
|
||||||
|
|
||||||
|
Random Access Iterator -> Random Access Traversal Iterator and Readable and Writable Iterator
|
||||||
|
``random_shuffle, sort, stable_sort, partial_sort, nth_element, push_heap, pop_heap
|
||||||
|
make_heap, sort_heap``
|
||||||
|
|
||||||
|
Input Iterator (2) -> Incrementable Iterator and Readable Iterator
|
||||||
|
``equal, mismatch``
|
||||||
|
|
||||||
|
Input Iterator (2) -> Incrementable Iterator and Readable Iterator
|
||||||
|
``transform``
|
||||||
|
|
||||||
|
Deprecations
|
||||||
|
++++++++++++
|
||||||
|
|
||||||
|
For the next working paper (but not for TR1), the committee should
|
||||||
|
consider deprecating the old iterator tags, and
|
||||||
|
std::iterator_traits, since it will be superceded by individual
|
||||||
|
traits metafunctions.
|
||||||
|
|
||||||
|
``vector<bool>``
|
||||||
|
++++++++++++++++
|
||||||
|
|
||||||
|
For the next working paper (but not for TR1), the committee should
|
||||||
|
consider reclassifying ``vector<bool>::iterator`` as a Random
|
||||||
|
Access Traversal Iterator and Readable Iterator and Writable
|
||||||
|
Iterator.
|
||||||
|
|
||||||
|
========
|
||||||
|
Design
|
||||||
|
========
|
||||||
|
|
||||||
|
The iterator requirements are to be separated into two groups. One set
|
||||||
|
of concepts handles the syntax and semantics of value access:
|
||||||
|
|
||||||
|
- Readable Iterator
|
||||||
|
- Writable Iterator
|
||||||
|
- Swappable Iterator
|
||||||
|
- Lvalue Iterator
|
||||||
|
|
||||||
|
The access concepts describe requirements related to ``operator*`` and
|
||||||
|
``operator->``, including the ``value_type``, ``reference``, and
|
||||||
|
``pointer`` associated types.
|
||||||
|
|
||||||
|
The other set of concepts handles traversal:
|
||||||
|
|
||||||
|
- Incrementable Iterator
|
||||||
|
- Single Pass Iterator
|
||||||
|
- Forward Traversal Iterator
|
||||||
|
- Bidirectional Traversal Iterator
|
||||||
|
- Random Access Traversal Iterator
|
||||||
|
|
||||||
|
The refinement relationships for the traversal concepts are in the
|
||||||
|
following diagram.
|
||||||
|
|
||||||
|
.. image:: traversal.png
|
||||||
|
|
||||||
|
In addition to the iterator movement operators, such as
|
||||||
|
``operator++``, the traversal concepts also include requirements on
|
||||||
|
position comparison such as ``operator==`` and ``operator<``. The
|
||||||
|
reason for the fine grain slicing of the concepts into the
|
||||||
|
Incrementable and Single Pass is to provide concepts that are exact
|
||||||
|
matches with the original input and output iterator requirements.
|
||||||
|
|
||||||
|
This proposal also includes a concept for specifying when an iterator
|
||||||
|
is interoperable with another iterator, in the sense that ``int*`` is
|
||||||
|
interoperable with ``int const*``.
|
||||||
|
|
||||||
|
- Interoperable Iterators
|
||||||
|
|
||||||
|
|
||||||
|
The relationship between the new iterator concepts and the old are
|
||||||
|
given in the following diagram.
|
||||||
|
|
||||||
|
.. image:: oldeqnew.png
|
||||||
|
|
||||||
|
Like the old iterator requirements, we provide tags for purposes of
|
||||||
|
dispatching based on the traversal concepts. The tags are related via
|
||||||
|
inheritance so that a tag is convertible to another tag if the concept
|
||||||
|
associated with the first tag is a refinement of the second tag.
|
||||||
|
|
||||||
|
Our design reuses ``iterator_traits<Iter>::iterator_category`` to
|
||||||
|
indicate an iterator's traversal capability. To specify
|
||||||
|
capabilities not captured by any old-style iterator category, an
|
||||||
|
iterator designer can use an ``iterator_category`` type that is
|
||||||
|
convertible to both the the most-derived old iterator category tag
|
||||||
|
which fits, and the appropriate new iterator traversal tag.
|
||||||
|
|
||||||
|
.. dwa2003/1/2: Note that we are not *requiring* convertibility to
|
||||||
|
a new-style traversal tag in order to meet new concepts.
|
||||||
|
Old-style iterators still fit, after all.
|
||||||
|
|
||||||
|
We do not provide tags for the purposes of dispatching based on the
|
||||||
|
access concepts, in part because we could not find a way to
|
||||||
|
automatically infer the right access tags for old-style iterators.
|
||||||
|
An iterator's writability may be dependent on the assignability of
|
||||||
|
its ``value_type`` and there's no known way to detect whether an
|
||||||
|
arbitrary type is assignable. Fortunately, the need for
|
||||||
|
dispatching based on access capability is not as great as the need
|
||||||
|
for dispatching based on traversal capability.
|
||||||
|
|
||||||
|
A difficult design decision concerned the ``operator[]``. The direct
|
||||||
|
approach for specifying ``operator[]`` would have a return type of
|
||||||
|
``reference``; the same as ``operator*``. However, going in this
|
||||||
|
direction would mean that an iterator satisfying the old Random Access
|
||||||
|
Iterator requirements would not necessarily be a model of Readable or
|
||||||
|
Writable Lvalue Iterator. Instead we have chosen a design that
|
||||||
|
matches the preferred resolution of `issue 299`_: ``operator[]`` is
|
||||||
|
only required to return something convertible to the ``value_type``
|
||||||
|
(for a Readable Iterator), and is required to support assignment
|
||||||
|
``i[n] = t`` (for a Writable Iterator).
|
||||||
|
|
||||||
|
|
||||||
|
===============
|
||||||
|
Proposed Text
|
||||||
|
===============
|
||||||
|
|
||||||
|
Addition to [lib.iterator.requirements]
|
||||||
|
=======================================
|
||||||
|
|
||||||
|
Iterator Value Access Concepts [lib.iterator.value.access]
|
||||||
|
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
|
||||||
|
|
||||||
|
In the tables below, ``X`` is an iterator type, ``a`` is a constant
|
||||||
|
object of type ``X``, ``R`` is
|
||||||
|
``std::iterator_traits<X>::reference``, ``T`` is
|
||||||
|
``std::iterator_traits<X>::value_type``, and ``v`` is a constant
|
||||||
|
object of type ``T``.
|
||||||
|
|
||||||
|
.. _Readable Iterator:
|
||||||
|
|
||||||
|
Readable Iterators [lib.readable.iterators]
|
||||||
|
-------------------------------------------
|
||||||
|
|
||||||
|
A class or built-in type ``X`` models the *Readable Iterator* concept
|
||||||
|
for value type ``T`` if, in addition to ``X`` being Assignable and
|
||||||
|
Copy Constructible, the following expressions are valid and respect
|
||||||
|
the stated semantics. ``U`` is the type of any specified member of
|
||||||
|
type ``T``.
|
||||||
|
|
||||||
|
+-----------------------------------------------------------------------------------------------------------------------------+
|
||||||
|
|Readable Iterator Requirements (in addition to Assignable and Copy Constructible) |
|
||||||
|
+-----------------------------------+------------------------+----------------------------------------------------------------+
|
||||||
|
|Expression |Return Type |Note/Precondition |
|
||||||
|
+===================================+========================+================================================================+
|
||||||
|
|``iterator_traits<X>::value_type`` |``T`` |Any non-reference, |
|
||||||
|
| | |non-cv-qualified type |
|
||||||
|
+-----------------------------------+------------------------+----------------------------------------------------------------+
|
||||||
|
|``*a`` | Convertible to ``T`` |pre: ``a`` is dereferenceable. If ``a == b`` then ``*a`` |
|
||||||
|
| | | is equivalent to ``*b``. |
|
||||||
|
+-----------------------------------+------------------------+----------------------------------------------------------------+
|
||||||
|
|``a->m`` |``U&`` |pre: ``pre: (*a).m`` is well-defined. Equivalent to ``(*a).m``. |
|
||||||
|
+-----------------------------------+------------------------+----------------------------------------------------------------+
|
||||||
|
|
||||||
|
.. We won't say anything about iterator_traits<X>::reference until the DR is resolved. -JGS
|
||||||
|
|
||||||
|
.. _Writable Iterator:
|
||||||
|
|
||||||
|
Writable Iterators [lib.writable.iterators]
|
||||||
|
-------------------------------------------
|
||||||
|
|
||||||
|
A class or built-in type ``X`` models the *Writable Iterator* concept
|
||||||
|
if, in addition to ``X`` being Copy Constructible, the following
|
||||||
|
expressions are valid and respect the stated semantics. Writable
|
||||||
|
Iterators have an associated *set of value types*.
|
||||||
|
|
||||||
|
+---------------------------------------------------------------------+
|
||||||
|
|Writable Iterator Requirements (in addition to Copy Constructible) |
|
||||||
|
+-------------------------+--------------+----------------------------+
|
||||||
|
|Expression |Return Type |Precondition |
|
||||||
|
+=========================+==============+============================+
|
||||||
|
|``*a = o`` | | pre: The type of ``o`` |
|
||||||
|
| | | is in the set of |
|
||||||
|
| | | value types of ``X`` |
|
||||||
|
+-------------------------+--------------+----------------------------+
|
||||||
|
|
||||||
|
Swappable Iterators [lib.swappable.iterators]
|
||||||
|
---------------------------------------------
|
||||||
|
|
||||||
|
A class or built-in type ``X`` models the *Swappable Iterator* concept
|
||||||
|
if, in addition to ``X`` being Copy Constructible, the following
|
||||||
|
expressions are valid and respect the stated semantics.
|
||||||
|
|
||||||
|
+---------------------------------------------------------------------+
|
||||||
|
|Swappable Iterator Requirements (in addition to Copy Constructible) |
|
||||||
|
+-------------------------+-------------+-----------------------------+
|
||||||
|
|Expression |Return Type |Postcondition |
|
||||||
|
+=========================+=============+=============================+
|
||||||
|
|``iter_swap(a, b)`` |``void`` |the pointed to values are |
|
||||||
|
| | |exchanged |
|
||||||
|
+-------------------------+-------------+-----------------------------+
|
||||||
|
|
||||||
|
[*Note:* An iterator that is a model of the `Readable Iterator`_ and
|
||||||
|
`Writable Iterator`_ concepts is also a model of *Swappable
|
||||||
|
Iterator*. *--end note*]
|
||||||
|
|
||||||
|
|
||||||
|
Lvalue Iterators [lib.lvalue.iterators]
|
||||||
|
---------------------------------------
|
||||||
|
|
||||||
|
The *Lvalue Iterator* concept adds the requirement that the return
|
||||||
|
type of ``operator*`` type be a reference to the value type of the
|
||||||
|
iterator.
|
||||||
|
|
||||||
|
+-------------------------------------------------------------+
|
||||||
|
| Lvalue Iterator Requirements |
|
||||||
|
+-------------+-----------+-----------------------------------+
|
||||||
|
|Expression |Return Type|Note/Assertion |
|
||||||
|
+=============+===========+===================================+
|
||||||
|
|``*a`` | ``T&`` |``T`` is *cv* |
|
||||||
|
| | |``iterator_traits<X>::value_type`` |
|
||||||
|
| | |where *cv* is an optional |
|
||||||
|
| | |cv-qualification. pre: ``a`` is |
|
||||||
|
| | |dereferenceable. |
|
||||||
|
+-------------+-----------+-----------------------------------+
|
||||||
|
|
||||||
|
If ``X`` is a `Writable Iterator`_ then ``a == b`` if and only if
|
||||||
|
``*a`` is the same object as ``*b``. If ``X`` is a `Readable
|
||||||
|
Iterator`_ then ``a == b`` implies ``*a`` is the same object as
|
||||||
|
``*b``.
|
||||||
|
|
||||||
|
|
||||||
|
Iterator Traversal Concepts [lib.iterator.traversal]
|
||||||
|
++++++++++++++++++++++++++++++++++++++++++++++++++++
|
||||||
|
|
||||||
|
In the tables below, ``X`` is an iterator type, ``a`` and ``b`` are
|
||||||
|
constant objects of type ``X``, ``r`` and ``s`` are mutable objects of
|
||||||
|
type ``X``, ``T`` is ``std::iterator_traits<X>::value_type``, and
|
||||||
|
``v`` is a constant object of type ``T``.
|
||||||
|
|
||||||
|
Incrementable Iterators [lib.incrementable.iterators]
|
||||||
|
-----------------------------------------------------
|
||||||
|
|
||||||
|
A class or built-in type ``X`` models the *Incrementable Iterator*
|
||||||
|
concept if, in addition to ``X`` being Assignable and Copy
|
||||||
|
Constructible, the following expressions are valid and respect the
|
||||||
|
stated semantics.
|
||||||
|
|
||||||
|
+------------------------------------------------------------------------------------+
|
||||||
|
|Incrementable Iterator Requirements (in addition to Assignable, Copy Constructible) |
|
||||||
|
| |
|
||||||
|
+--------------------------------+-------------------------------+-------------------+
|
||||||
|
|Expression |Return Type |Assertion |
|
||||||
|
+================================+===============================+===================+
|
||||||
|
|``++r`` |``X&`` |``&r == &++r`` |
|
||||||
|
+--------------------------------+-------------------------------+-------------------+
|
||||||
|
|``r++`` | | |
|
||||||
|
+--------------------------------+-------------------------------+-------------------+
|
||||||
|
|``*r++`` | | |
|
||||||
|
+--------------------------------+-------------------------------+-------------------+
|
||||||
|
|``iterator_traversal<X>::type`` |Convertible to | |
|
||||||
|
| |``incrementable_traversal_tag``| |
|
||||||
|
+--------------------------------+-------------------------------+-------------------+
|
||||||
|
|
||||||
|
|
||||||
|
If ``X`` is a `Writable Iterator`_ then ``X a(r++);`` is equivalent
|
||||||
|
to ``X a(r); ++r;`` and ``*r++ = o`` is equivalent
|
||||||
|
to ``*r = o; ++r``.
|
||||||
|
If ``X`` is a `Readable Iterator`_ then ``T z(*r++);`` is equivalent
|
||||||
|
to ``T z(*r); ++r;``.
|
||||||
|
|
||||||
|
.. TR1: incrementable_iterator_tag changed to
|
||||||
|
incrementable_traversal_tag for consistency.
|
||||||
|
|
||||||
|
Single Pass Iterators [lib.single.pass.iterators]
|
||||||
|
-------------------------------------------------
|
||||||
|
|
||||||
|
A class or built-in type ``X`` models the *Single Pass Iterator*
|
||||||
|
concept if the following expressions are valid and respect the stated
|
||||||
|
semantics.
|
||||||
|
|
||||||
|
|
||||||
|
+----------------------------------------------------------------------------------------------------------------+
|
||||||
|
|Single Pass Iterator Requirements (in addition to Incrementable Iterator and Equality Comparable) |
|
||||||
|
| |
|
||||||
|
+----------------------------------------+-----------------------------+-------------+---------------------------+
|
||||||
|
|Expression |Return Type | Operational |Assertion/ |
|
||||||
|
| | | Semantics |Pre-/Post-condition |
|
||||||
|
+========================================+=============================+=============+===========================+
|
||||||
|
|``++r`` |``X&`` | |pre: ``r`` is |
|
||||||
|
| | | |dereferenceable; post: |
|
||||||
|
| | | |``r`` is dereferenceable or|
|
||||||
|
| | | |``r`` is past-the-end |
|
||||||
|
+----------------------------------------+-----------------------------+-------------+---------------------------+
|
||||||
|
|``a == b`` |convertible to ``bool`` | |``==`` is an equivalence |
|
||||||
|
| | | |relation over its domain |
|
||||||
|
+----------------------------------------+-----------------------------+-------------+---------------------------+
|
||||||
|
|``a != b`` |convertible to ``bool`` |``!(a == b)``| |
|
||||||
|
+----------------------------------------+-----------------------------+-------------+---------------------------+
|
||||||
|
|``iterator_traits<X>::difference_type`` |A signed integral type | | |
|
||||||
|
| |representing the distance | | |
|
||||||
|
| |between iterators | | |
|
||||||
|
+----------------------------------------+-----------------------------+-------------+---------------------------+
|
||||||
|
|``iterator_traversal<X>::type`` |Convertible to | | |
|
||||||
|
| |``single_pass_traversal_tag``| | |
|
||||||
|
+----------------------------------------+-----------------------------+-------------+---------------------------+
|
||||||
|
|
||||||
|
.. TR1: single_pass_iterator_tag changed to
|
||||||
|
single_pass_traversal_tag for consistency
|
||||||
|
|
||||||
|
|
||||||
|
Forward Traversal Iterators [lib.forward.traversal.iterators]
|
||||||
|
-------------------------------------------------------------
|
||||||
|
|
||||||
|
A class or built-in type ``X`` models the *Forward Traversal Iterator*
|
||||||
|
concept if, in addition to ``X`` meeting the requirements of Default
|
||||||
|
Constructible and Single Pass Iterator, the following expressions are
|
||||||
|
valid and respect the stated semantics.
|
||||||
|
|
||||||
|
+--------------------------------------------------------------------------------------------------------+
|
||||||
|
|Forward Traversal Iterator Requirements (in addition to Default Constructible and Single Pass Iterator) |
|
||||||
|
+---------------------------------------+-----------------------------------+----------------------------+
|
||||||
|
|Expression |Return Type |Assertion/Note |
|
||||||
|
+=======================================+===================================+============================+
|
||||||
|
|``X u;`` |``X&`` |note: ``u`` may have a |
|
||||||
|
| | |singular value. |
|
||||||
|
+---------------------------------------+-----------------------------------+----------------------------+
|
||||||
|
|``++r`` |``X&`` |``r == s`` and ``r`` is |
|
||||||
|
| | |dereferenceable implies |
|
||||||
|
| | |``++r == ++s.`` |
|
||||||
|
+---------------------------------------+-----------------------------------+----------------------------+
|
||||||
|
|``iterator_traversal<X>::type`` |Convertible to | |
|
||||||
|
| |``forward_traversal_tag`` | |
|
||||||
|
+---------------------------------------+-----------------------------------+----------------------------+
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
.. TR1: forward_traversal_iterator_tag changed to
|
||||||
|
forward_traversal_tag for consistency
|
||||||
|
|
||||||
|
|
||||||
|
Bidirectional Traversal Iterators [lib.bidirectional.traversal.iterators]
|
||||||
|
-------------------------------------------------------------------------
|
||||||
|
|
||||||
|
A class or built-in type ``X`` models the *Bidirectional Traversal
|
||||||
|
Iterator* concept if, in addition to ``X`` meeting the requirements of
|
||||||
|
Forward Traversal Iterator, the following expressions are valid and
|
||||||
|
respect the stated semantics.
|
||||||
|
|
||||||
|
+-----------------------------------------------------------------------------------------------------+
|
||||||
|
|Bidirectional Traversal Iterator Requirements (in addition to Forward Traversal |
|
||||||
|
|Iterator) |
|
||||||
|
+--------------------------------+-------------------------------+--------------+---------------------+
|
||||||
|
|Expression |Return Type | Operational |Assertion/ |
|
||||||
|
| | | Semantics |Pre-/Post-condition |
|
||||||
|
+================================+===============================+==============+=====================+
|
||||||
|
|``--r`` |``X&`` | |pre: there exists |
|
||||||
|
| | | |``s`` such that ``r |
|
||||||
|
| | | |== ++s``. post: |
|
||||||
|
| | | |``s`` is |
|
||||||
|
| | | |dereferenceable. |
|
||||||
|
| | | | |
|
||||||
|
| | | |``++(--r) == r``. |
|
||||||
|
| | | |``--r == --s`` |
|
||||||
|
| | | |implies ``r == |
|
||||||
|
| | | |s``. ``&r == &--r``. |
|
||||||
|
+--------------------------------+-------------------------------+--------------+---------------------+
|
||||||
|
|``r--`` |convertible to ``const X&`` |:: | |
|
||||||
|
| | | | |
|
||||||
|
| | | { | |
|
||||||
|
| | | X tmp = r; | |
|
||||||
|
| | | --r; | |
|
||||||
|
| | | return tmp;| |
|
||||||
|
| | | } | |
|
||||||
|
+--------------------------------+-------------------------------+--------------+---------------------+
|
||||||
|
|``iterator_traversal<X>::type`` |Convertible to | | |
|
||||||
|
| |``bidirectional_traversal_tag``| | |
|
||||||
|
| | | | |
|
||||||
|
+--------------------------------+-------------------------------+--------------+---------------------+
|
||||||
|
|
||||||
|
.. TR1: bidirectional_traversal_iterator_tag changed to
|
||||||
|
bidirectional_traversal_tag for consistency
|
||||||
|
|
||||||
|
Random Access Traversal Iterators [lib.random.access.traversal.iterators]
|
||||||
|
-------------------------------------------------------------------------
|
||||||
|
|
||||||
|
A class or built-in type ``X`` models the *Random Access Traversal
|
||||||
|
Iterator* concept if the following expressions are valid and respect
|
||||||
|
the stated semantics. In the table below, ``Distance`` is
|
||||||
|
``iterator_traits<X>::difference_type`` and ``n`` represents a
|
||||||
|
constant object of type ``Distance``.
|
||||||
|
|
||||||
|
+------------------------------------------------------------------------------------------------------------------+
|
||||||
|
|Random Access Traversal Iterator Requirements (in addition to Bidirectional Traversal Iterator) |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|Expression |Return Type |Operational Semantics |Assertion/ |
|
||||||
|
| | | |Precondition |
|
||||||
|
+===============================+=================================+=========================+======================+
|
||||||
|
|``r += n`` |``X&`` |:: | |
|
||||||
|
| | | | |
|
||||||
|
| | | { | |
|
||||||
|
| | | Distance m = n; | |
|
||||||
|
| | | if (m >= 0) | |
|
||||||
|
| | | while (m--) | |
|
||||||
|
| | | ++r; | |
|
||||||
|
| | | else | |
|
||||||
|
| | | while (m++) | |
|
||||||
|
| | | --r; | |
|
||||||
|
| | | return r; | |
|
||||||
|
| | | } | |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``a + n``, ``n + a`` |``X`` |``{ X tmp = a; return tmp| |
|
||||||
|
| | |+= n; }`` | |
|
||||||
|
| | | | |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``r -= n`` |``X&`` |``return r += -n`` | |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``a - n`` |``X`` |``{ X tmp = a; return tmp| |
|
||||||
|
| | |-= n; }`` | |
|
||||||
|
| | | | |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``b - a`` |``Distance`` |``a < b ? distance(a,b) |pre: there exists a |
|
||||||
|
| | |: -distance(b,a)`` |value ``n`` of |
|
||||||
|
| | | |``Distance`` such that|
|
||||||
|
| | | |``a + n == b``. ``b |
|
||||||
|
| | | |== a + (b - a)``. |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``a[n]`` |convertible to T |``*(a + n)`` |pre: a is a `Readable |
|
||||||
|
| | | |Iterator`_ |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``a[n] = v`` |convertible to T |``*(a + n) = v`` |pre: a is a `Writable |
|
||||||
|
| | | |Iterator`_ |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``a < b`` |convertible to ``bool`` |``b - a > 0`` |``<`` is a total |
|
||||||
|
| | | |ordering relation |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``a > b`` |convertible to ``bool`` |``b < a`` |``>`` is a total |
|
||||||
|
| | | |ordering relation |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``a >= b`` |convertible to ``bool`` |``!(a < b)`` | |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``a <= b`` |convertible to ``bool`` |``!(a > b)`` | |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|``iterator_traversal<X>::type``|Convertible to | | |
|
||||||
|
| |``random_access_traversal_tag`` | | |
|
||||||
|
+-------------------------------+---------------------------------+-------------------------+----------------------+
|
||||||
|
|
||||||
|
.. TR1: random_access_traversal_iterator_tag changed to
|
||||||
|
random_access_traversal_tag for consistency
|
||||||
|
|
||||||
|
|
||||||
|
Interoperable Iterators [lib.interoperable.iterators]
|
||||||
|
-----------------------------------------------------
|
||||||
|
|
||||||
|
A class or built-in type ``X`` that models Single Pass Iterator is
|
||||||
|
*interoperable with* a class or built-in type ``Y`` that also models
|
||||||
|
Single Pass Iterator if the following expressions are valid and
|
||||||
|
respect the stated semantics. In the tables below, ``x`` is an object
|
||||||
|
of type ``X``, ``y`` is an object of type ``Y``, ``Distance`` is
|
||||||
|
``iterator_traits<Y>::difference_type``, and ``n`` represents a
|
||||||
|
constant object of type ``Distance``.
|
||||||
|
|
||||||
|
+-----------+-----------------------+---------------------------------------------------+
|
||||||
|
|Expression |Return Type |Assertion/Precondition/Postcondition |
|
||||||
|
+===========+=======================+===================================================+
|
||||||
|
|``y = x`` |``Y`` |post: ``y == x`` |
|
||||||
|
+-----------+-----------------------+---------------------------------------------------+
|
||||||
|
|``Y(x)`` |``Y`` |post: ``Y(x) == x`` |
|
||||||
|
+-----------+-----------------------+---------------------------------------------------+
|
||||||
|
|``x == y`` |convertible to ``bool``|``==`` is an equivalence relation over its domain. |
|
||||||
|
+-----------+-----------------------+---------------------------------------------------+
|
||||||
|
|``y == x`` |convertible to ``bool``|``==`` is an equivalence relation over its domain. |
|
||||||
|
+-----------+-----------------------+---------------------------------------------------+
|
||||||
|
|``x != y`` |convertible to ``bool``|``bool(a==b) != bool(a!=b)`` over its domain. |
|
||||||
|
+-----------+-----------------------+---------------------------------------------------+
|
||||||
|
|``y != x`` |convertible to ``bool``|``bool(a==b) != bool(a!=b)`` over its domain. |
|
||||||
|
+-----------+-----------------------+---------------------------------------------------+
|
||||||
|
|
||||||
|
If ``X`` and ``Y`` both model Random Access Traversal Iterator then
|
||||||
|
the following additional requirements must be met.
|
||||||
|
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|Expression |Return Type |Operational Semantics|Assertion/ Precondition |
|
||||||
|
+===========+=======================+=====================+======================================+
|
||||||
|
|``x < y`` |convertible to ``bool``|``y - x > 0`` |``<`` is a total ordering relation |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|``y < x`` |convertible to ``bool``|``x - y > 0`` |``<`` is a total ordering relation |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|``x > y`` |convertible to ``bool``|``y < x`` |``>`` is a total ordering relation |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|``y > x`` |convertible to ``bool``|``x < y`` |``>`` is a total ordering relation |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|``x >= y`` |convertible to ``bool``|``!(x < y)`` | |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|``y >= x`` |convertible to ``bool``|``!(y < x)`` | |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|``x <= y`` |convertible to ``bool``|``!(x > y)`` | |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|``y <= x`` |convertible to ``bool``|``!(y > x)`` | |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|``y - x`` |``Distance`` |``distance(Y(x),y)`` |pre: there exists a value ``n`` of |
|
||||||
|
| | | |``Distance`` such that ``x + n == y``.|
|
||||||
|
| | | |``y == x + (y - x)``. |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|``x - y`` |``Distance`` |``distance(y,Y(x))`` |pre: there exists a value ``n`` of |
|
||||||
|
| | | |``Distance`` such that ``y + n == x``.|
|
||||||
|
| | | |``x == y + (x - y)``. |
|
||||||
|
+-----------+-----------------------+---------------------+--------------------------------------+
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
Addition to [lib.iterator.synopsis]
|
||||||
|
===================================
|
||||||
|
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
// lib.iterator.traits, traits and tags
|
||||||
|
template <class Iterator> struct is_readable_iterator;
|
||||||
|
template <class Iterator> struct iterator_traversal;
|
||||||
|
|
||||||
|
struct incrementable_traversal_tag { };
|
||||||
|
struct single_pass_traversal_tag : incrementable_traversal_tag { };
|
||||||
|
struct forward_traversal_tag : single_pass_traversal_tag { };
|
||||||
|
struct bidirectional_traversal_tag : forward_traversal_tag { };
|
||||||
|
struct random_access_traversal_tag : bidirectional_traversal_tag { };
|
||||||
|
|
||||||
|
Addition to [lib.iterator.traits]
|
||||||
|
=================================
|
||||||
|
|
||||||
|
The ``is_readable_iterator`` class
|
||||||
|
template satisfies the UnaryTypeTrait_ requirements.
|
||||||
|
|
||||||
|
Given an iterator type ``X``, ``is_readable_iterator<X>::value``
|
||||||
|
yields ``true`` if, for an object ``a`` of type ``X``, ``*a`` is
|
||||||
|
convertible to ``iterator_traits<X>::value_type``, and ``false``
|
||||||
|
otherwise.
|
||||||
|
|
||||||
|
``iterator_traversal<X>::type`` is
|
||||||
|
|
||||||
|
.. parsed-literal::
|
||||||
|
|
||||||
|
*category-to-traversal*\ (iterator_traits<X>::iterator_category)
|
||||||
|
|
||||||
|
where *category-to-traversal* is defined as follows
|
||||||
|
|
||||||
|
.. _`category-to-traversal`:
|
||||||
|
|
||||||
|
.. parsed-literal::
|
||||||
|
|
||||||
|
*category-to-traversal*\ (C) =
|
||||||
|
if (C is convertible to incrementable_traversal_tag)
|
||||||
|
return C;
|
||||||
|
else if (C is convertible to random_access_iterator_tag)
|
||||||
|
return random_access_traversal_tag;
|
||||||
|
else if (C is convertible to bidirectional_iterator_tag)
|
||||||
|
return bidirectional_traversal_tag;
|
||||||
|
else if (C is convertible to forward_iterator_tag)
|
||||||
|
return forward_traversal_tag;
|
||||||
|
else if (C is convertible to input_iterator_tag)
|
||||||
|
return single_pass_traversal_tag;
|
||||||
|
else if (C is convertible to output_iterator_tag)
|
||||||
|
return incrementable_traversal_tag;
|
||||||
|
else
|
||||||
|
*the program is ill-formed*
|
||||||
|
|
||||||
|
|
||||||
|
===========
|
||||||
|
Footnotes
|
||||||
|
===========
|
||||||
|
|
||||||
|
.. _UnaryTypeTrait: n1519_
|
||||||
|
|
||||||
|
The UnaryTypeTrait concept is defined in n1519_; the LWG is
|
||||||
|
considering adding the requirement that specializations are derived
|
||||||
|
from their nested ``::type``.
|
||||||
|
|
||||||
|
.. _n1519: http://anubis.dkuug.dk/jtc1/sc22/wg21/docs/papers/2003/n1519.htm
|
||||||
|
|
||||||
|
..
|
||||||
|
LocalWords: Abrahams Siek Witt const bool Sutter's WG int UL LI href Lvalue
|
||||||
|
LocalWords: ReadableIterator WritableIterator SwappableIterator cv pre iter
|
||||||
|
LocalWords: ConstantLvalueIterator MutableLvalueIterator CopyConstructible TR
|
||||||
|
LocalWords: ForwardTraversalIterator BidirectionalTraversalIterator lvalue
|
||||||
|
LocalWords: RandomAccessTraversalIterator dereferenceable Incrementable tmp
|
||||||
|
LocalWords: incrementable xxx min prev inplace png oldeqnew AccessTag struct
|
||||||
|
LocalWords: TraversalTag typename lvalues DWA Hmm JGS mis enum
|
BIN
doc/oldeqnew.png
Normal file
BIN
doc/oldeqnew.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 33 KiB |
8
doc/permutation_iter_abstract.rst
Normal file
8
doc/permutation_iter_abstract.rst
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
The permutation iterator adaptor provides a permuted view of a given
|
||||||
|
range. That is, the view includes every element of the given range but
|
||||||
|
in a potentially different order.
|
||||||
|
|
311
doc/permutation_iterator.html
Normal file
311
doc/permutation_iterator.html
Normal file
@ -0,0 +1,311 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" />
|
||||||
|
<title>Permutation Iterator</title>
|
||||||
|
<meta name="author" content="Toon Knapen, David Abrahams, Roland Richter, Jeremy Siek" />
|
||||||
|
<meta name="organization" content="Boost Consulting, Indiana University Open Systems Lab" />
|
||||||
|
<meta name="date" content="2006-09-11" />
|
||||||
|
<meta name="copyright" content="Copyright Toon Knapen, David Abrahams, Roland Richter, and Jeremy Siek 2003." />
|
||||||
|
<link rel="stylesheet" href="../../../rst.css" type="text/css" />
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="permutation-iterator">
|
||||||
|
<h1 class="title">Permutation Iterator</h1>
|
||||||
|
<table class="docinfo" frame="void" rules="none">
|
||||||
|
<col class="docinfo-name" />
|
||||||
|
<col class="docinfo-content" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr><th class="docinfo-name">Author:</th>
|
||||||
|
<td>Toon Knapen, David Abrahams, Roland Richter, Jeremy Siek</td></tr>
|
||||||
|
<tr><th class="docinfo-name">Contact:</th>
|
||||||
|
<td><a class="first reference external" href="mailto:dave@boost-consulting.com">dave@boost-consulting.com</a>, <a class="last reference external" href="mailto:jsiek@osl.iu.edu">jsiek@osl.iu.edu</a></td></tr>
|
||||||
|
<tr><th class="docinfo-name">Organization:</th>
|
||||||
|
<td><a class="first reference external" href="http://www.boost-consulting.com">Boost Consulting</a>, Indiana University <a class="last reference external" href="http://www.osl.iu.edu">Open Systems
|
||||||
|
Lab</a></td></tr>
|
||||||
|
<tr><th class="docinfo-name">Date:</th>
|
||||||
|
<td>2006-09-11</td></tr>
|
||||||
|
<tr><th class="docinfo-name">Copyright:</th>
|
||||||
|
<td>Copyright Toon Knapen, David Abrahams, Roland Richter, and Jeremy Siek 2003.</td></tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<!-- Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">abstract:</th><td class="field-body"><!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
The permutation iterator adaptor provides a permuted view of a given
|
||||||
|
range. That is, the view includes every element of the given range but
|
||||||
|
in a potentially different order.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<div class="contents topic" id="table-of-contents">
|
||||||
|
<p class="topic-title first">Table of Contents</p>
|
||||||
|
<ul class="simple">
|
||||||
|
<li><a class="reference internal" href="#introduction" id="id2">Introduction</a></li>
|
||||||
|
<li><a class="reference internal" href="#reference" id="id3">Reference</a><ul>
|
||||||
|
<li><a class="reference internal" href="#permutation-iterator-requirements" id="id4"><tt class="docutils literal"><span class="pre">permutation_iterator</span></tt> requirements</a></li>
|
||||||
|
<li><a class="reference internal" href="#permutation-iterator-models" id="id5"><tt class="docutils literal"><span class="pre">permutation_iterator</span></tt> models</a></li>
|
||||||
|
<li><a class="reference internal" href="#permutation-iterator-operations" id="id6"><tt class="docutils literal"><span class="pre">permutation_iterator</span></tt> operations</a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#example" id="id7">Example</a></li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="introduction">
|
||||||
|
<h1><a class="toc-backref" href="#id2">Introduction</a></h1>
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<p>The adaptor takes two arguments:</p>
|
||||||
|
<blockquote>
|
||||||
|
<ul class="simple">
|
||||||
|
<li>an iterator to the range V on which the permutation
|
||||||
|
will be applied</li>
|
||||||
|
<li>the reindexing scheme that defines how the
|
||||||
|
elements of V will be permuted.</li>
|
||||||
|
</ul>
|
||||||
|
</blockquote>
|
||||||
|
<p>Note that the permutation iterator is not limited to strict
|
||||||
|
permutations of the given range V. The distance between begin and end
|
||||||
|
of the reindexing iterators is allowed to be smaller compared to the
|
||||||
|
size of the range V, in which case the permutation iterator only
|
||||||
|
provides a permutation of a subrange of V. The indexes neither need
|
||||||
|
to be unique. In this same context, it must be noted that the past the
|
||||||
|
end permutation iterator is completely defined by means of the
|
||||||
|
past-the-end iterator to the indices.</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="reference">
|
||||||
|
<h1><a class="toc-backref" href="#id3">Reference</a></h1>
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<pre class="literal-block">
|
||||||
|
template< class ElementIterator
|
||||||
|
, class IndexIterator
|
||||||
|
, class ValueT = use_default
|
||||||
|
, class CategoryT = use_default
|
||||||
|
, class ReferenceT = use_default
|
||||||
|
, class DifferenceT = use_default >
|
||||||
|
class permutation_iterator
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
permutation_iterator();
|
||||||
|
explicit permutation_iterator(ElementIterator x, IndexIterator y);
|
||||||
|
|
||||||
|
template< class OEIter, class OIIter, class V, class C, class R, class D >
|
||||||
|
permutation_iterator(
|
||||||
|
permutation_iterator<OEIter, OIIter, V, C, R, D> const& r
|
||||||
|
, typename enable_if_convertible<OEIter, ElementIterator>::type* = 0
|
||||||
|
, typename enable_if_convertible<OIIter, IndexIterator>::type* = 0
|
||||||
|
);
|
||||||
|
reference operator*() const;
|
||||||
|
permutation_iterator& operator++();
|
||||||
|
ElementIterator const& base() const;
|
||||||
|
private:
|
||||||
|
ElementIterator m_elt; // exposition only
|
||||||
|
IndexIterator m_order; // exposition only
|
||||||
|
};
|
||||||
|
|
||||||
|
template <class ElementIterator, class IndexIterator>
|
||||||
|
permutation_iterator<ElementIterator, IndexIterator>
|
||||||
|
make_permutation_iterator( ElementIterator e, IndexIterator i);
|
||||||
|
</pre>
|
||||||
|
<div class="section" id="permutation-iterator-requirements">
|
||||||
|
<h2><a class="toc-backref" href="#id4"><tt class="docutils literal"><span class="pre">permutation_iterator</span></tt> requirements</a></h2>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">ElementIterator</span></tt> shall model Random Access Traversal Iterator.
|
||||||
|
<tt class="docutils literal"><span class="pre">IndexIterator</span></tt> shall model Readable Iterator. The value type of
|
||||||
|
the <tt class="docutils literal"><span class="pre">IndexIterator</span></tt> must be convertible to the difference type of
|
||||||
|
<tt class="docutils literal"><span class="pre">ElementIterator</span></tt>.</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="permutation-iterator-models">
|
||||||
|
<h2><a class="toc-backref" href="#id5"><tt class="docutils literal"><span class="pre">permutation_iterator</span></tt> models</a></h2>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">permutation_iterator</span></tt> models the same iterator traversal concepts
|
||||||
|
as <tt class="docutils literal"><span class="pre">IndexIterator</span></tt> and the same iterator access concepts as
|
||||||
|
<tt class="docutils literal"><span class="pre">ElementIterator</span></tt>.</p>
|
||||||
|
<p>If <tt class="docutils literal"><span class="pre">IndexIterator</span></tt> models Single Pass Iterator and
|
||||||
|
<tt class="docutils literal"><span class="pre">ElementIterator</span></tt> models Readable Iterator then
|
||||||
|
<tt class="docutils literal"><span class="pre">permutation_iterator</span></tt> models Input Iterator.</p>
|
||||||
|
<p>If <tt class="docutils literal"><span class="pre">IndexIterator</span></tt> models Forward Traversal Iterator and
|
||||||
|
<tt class="docutils literal"><span class="pre">ElementIterator</span></tt> models Readable Lvalue Iterator then
|
||||||
|
<tt class="docutils literal"><span class="pre">permutation_iterator</span></tt> models Forward Iterator.</p>
|
||||||
|
<p>If <tt class="docutils literal"><span class="pre">IndexIterator</span></tt> models Bidirectional Traversal Iterator and
|
||||||
|
<tt class="docutils literal"><span class="pre">ElementIterator</span></tt> models Readable Lvalue Iterator then
|
||||||
|
<tt class="docutils literal"><span class="pre">permutation_iterator</span></tt> models Bidirectional Iterator.</p>
|
||||||
|
<p>If <tt class="docutils literal"><span class="pre">IndexIterator</span></tt> models Random Access Traversal Iterator and
|
||||||
|
<tt class="docutils literal"><span class="pre">ElementIterator</span></tt> models Readable Lvalue Iterator then
|
||||||
|
<tt class="docutils literal"><span class="pre">permutation_iterator</span></tt> models Random Access Iterator.</p>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">permutation_iterator<E1,</span> <span class="pre">X,</span> <span class="pre">V1,</span> <span class="pre">C2,</span> <span class="pre">R1,</span> <span class="pre">D1></span></tt> is interoperable
|
||||||
|
with <tt class="docutils literal"><span class="pre">permutation_iterator<E2,</span> <span class="pre">Y,</span> <span class="pre">V2,</span> <span class="pre">C2,</span> <span class="pre">R2,</span> <span class="pre">D2></span></tt> if and only if
|
||||||
|
<tt class="docutils literal"><span class="pre">X</span></tt> is interoperable with <tt class="docutils literal"><span class="pre">Y</span></tt> and <tt class="docutils literal"><span class="pre">E1</span></tt> is convertible
|
||||||
|
to <tt class="docutils literal"><span class="pre">E2</span></tt>.</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="permutation-iterator-operations">
|
||||||
|
<h2><a class="toc-backref" href="#id6"><tt class="docutils literal"><span class="pre">permutation_iterator</span></tt> operations</a></h2>
|
||||||
|
<p>In addition to those operations required by the concepts that
|
||||||
|
<tt class="docutils literal"><span class="pre">permutation_iterator</span></tt> models, <tt class="docutils literal"><span class="pre">permutation_iterator</span></tt> provides the
|
||||||
|
following operations.</p>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">permutation_iterator();</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body">Default constructs <tt class="docutils literal"><span class="pre">m_elt</span></tt> and <tt class="docutils literal"><span class="pre">m_order</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">explicit</span> <span class="pre">permutation_iterator(ElementIterator</span> <span class="pre">x,</span> <span class="pre">IndexIterator</span> <span class="pre">y);</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body">Constructs <tt class="docutils literal"><span class="pre">m_elt</span></tt> from <tt class="docutils literal"><span class="pre">x</span></tt> and <tt class="docutils literal"><span class="pre">m_order</span></tt> from <tt class="docutils literal"><span class="pre">y</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<pre class="literal-block">
|
||||||
|
template< class OEIter, class OIIter, class V, class C, class R, class D >
|
||||||
|
permutation_iterator(
|
||||||
|
permutation_iterator<OEIter, OIIter, V, C, R, D> const& r
|
||||||
|
, typename enable_if_convertible<OEIter, ElementIterator>::type* = 0
|
||||||
|
, typename enable_if_convertible<OIIter, IndexIterator>::type* = 0
|
||||||
|
);
|
||||||
|
</pre>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body">Constructs <tt class="docutils literal"><span class="pre">m_elt</span></tt> from <tt class="docutils literal"><span class="pre">r.m_elt</span></tt> and
|
||||||
|
<tt class="docutils literal"><span class="pre">m_order</span></tt> from <tt class="docutils literal"><span class="pre">y.m_order</span></tt>.</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">reference</span> <span class="pre">operator*()</span> <span class="pre">const;</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">*(m_elt</span> <span class="pre">+</span> <span class="pre">*m_order)</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">permutation_iterator&</span> <span class="pre">operator++();</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Effects:</th><td class="field-body"><tt class="docutils literal"><span class="pre">++m_order</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">*this</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<p><tt class="docutils literal"><span class="pre">ElementIterator</span> <span class="pre">const&</span> <span class="pre">base()</span> <span class="pre">const;</span></tt></p>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">m_order</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<pre class="literal-block">
|
||||||
|
template <class ElementIterator, class IndexIterator>
|
||||||
|
permutation_iterator<ElementIterator, IndexIterator>
|
||||||
|
make_permutation_iterator(ElementIterator e, IndexIterator i);
|
||||||
|
</pre>
|
||||||
|
<table class="docutils field-list" frame="void" rules="none">
|
||||||
|
<col class="field-name" />
|
||||||
|
<col class="field-body" />
|
||||||
|
<tbody valign="top">
|
||||||
|
<tr class="field"><th class="field-name">Returns:</th><td class="field-body"><tt class="docutils literal"><span class="pre">permutation_iterator<ElementIterator,</span> <span class="pre">IndexIterator>(e,</span> <span class="pre">i)</span></tt></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="example">
|
||||||
|
<h1><a class="toc-backref" href="#id7">Example</a></h1>
|
||||||
|
<!-- Copyright David Abrahams 2006. Distributed under the Boost -->
|
||||||
|
<!-- Software License, Version 1.0. (See accompanying -->
|
||||||
|
<!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
|
||||||
|
<pre class="literal-block">
|
||||||
|
using namespace boost;
|
||||||
|
int i = 0;
|
||||||
|
|
||||||
|
typedef std::vector< int > element_range_type;
|
||||||
|
typedef std::list< int > index_type;
|
||||||
|
|
||||||
|
static const int element_range_size = 10;
|
||||||
|
static const int index_size = 4;
|
||||||
|
|
||||||
|
element_range_type elements( element_range_size );
|
||||||
|
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 );
|
||||||
|
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() );
|
||||||
|
|
||||||
|
typedef permutation_iterator< element_range_type::iterator, index_type::iterator > permutation_type;
|
||||||
|
permutation_type begin = make_permutation_iterator( elements.begin(), indices.begin() );
|
||||||
|
permutation_type it = begin;
|
||||||
|
permutation_type end = make_permutation_iterator( elements.begin(), indices.end() );
|
||||||
|
|
||||||
|
std::cout << "The original range is : ";
|
||||||
|
std::copy( elements.begin(), elements.end(), std::ostream_iterator< int >( std::cout, " " ) );
|
||||||
|
std::cout << "\n";
|
||||||
|
|
||||||
|
std::cout << "The reindexing scheme is : ";
|
||||||
|
std::copy( indices.begin(), indices.end(), std::ostream_iterator< int >( std::cout, " " ) );
|
||||||
|
std::cout << "\n";
|
||||||
|
|
||||||
|
std::cout << "The permutated range is : ";
|
||||||
|
std::copy( begin, end, std::ostream_iterator< int >( std::cout, " " ) );
|
||||||
|
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>
|
||||||
|
<p>The output is:</p>
|
||||||
|
<pre class="literal-block">
|
||||||
|
The original range is : 0 1 2 3 4 5 6 7 8 9
|
||||||
|
The reindexing scheme is : 9 8 7 6
|
||||||
|
The permutated range is : 9 8 7 6
|
||||||
|
Elements at even indices in the permutation : 9 7
|
||||||
|
Permutation backwards : 6 7 8 9
|
||||||
|
Iterate backward with stride 2 : 6 8
|
||||||
|
</pre>
|
||||||
|
<p>The source code for this example can be found <a class="reference external" href="../example/permutation_iter_example.cpp">here</a>.</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<hr class="footer" />
|
||||||
|
<a class="reference external" href="permutation_iterator.rst">View document source</a>.
|
||||||
|
Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
BIN
doc/permutation_iterator.pdf
Normal file
BIN
doc/permutation_iterator.pdf
Normal file
Binary file not shown.
41
doc/permutation_iterator.rst
Normal file
41
doc/permutation_iterator.rst
Normal file
@ -0,0 +1,41 @@
|
|||||||
|
.. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
++++++++++++++++++++++
|
||||||
|
Permutation Iterator
|
||||||
|
++++++++++++++++++++++
|
||||||
|
|
||||||
|
:Author: Toon Knapen, David Abrahams, Roland Richter, Jeremy Siek
|
||||||
|
:Contact: dave@boost-consulting.com, jsiek@osl.iu.edu
|
||||||
|
:organization: `Boost Consulting`_, Indiana University `Open Systems
|
||||||
|
Lab`_
|
||||||
|
:date: $Date$
|
||||||
|
:copyright: Copyright Toon Knapen, David Abrahams, Roland Richter, and Jeremy Siek 2003.
|
||||||
|
|
||||||
|
.. _`Boost Consulting`: http://www.boost-consulting.com
|
||||||
|
.. _`Open Systems Lab`: http://www.osl.iu.edu
|
||||||
|
|
||||||
|
:abstract:
|
||||||
|
|
||||||
|
.. include:: permutation_iter_abstract.rst
|
||||||
|
|
||||||
|
.. contents:: Table of Contents
|
||||||
|
|
||||||
|
|
||||||
|
Introduction
|
||||||
|
============
|
||||||
|
|
||||||
|
.. include:: permutation_iterator_body.rst
|
||||||
|
|
||||||
|
|
||||||
|
Reference
|
||||||
|
=========
|
||||||
|
|
||||||
|
.. include:: permutation_iterator_ref.rst
|
||||||
|
|
||||||
|
|
||||||
|
Example
|
||||||
|
=======
|
||||||
|
|
||||||
|
.. include:: permutation_iterator_eg.rst
|
19
doc/permutation_iterator_body.rst
Normal file
19
doc/permutation_iterator_body.rst
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
The adaptor takes two arguments:
|
||||||
|
|
||||||
|
* an iterator to the range V on which the permutation
|
||||||
|
will be applied
|
||||||
|
* the reindexing scheme that defines how the
|
||||||
|
elements of V will be permuted.
|
||||||
|
|
||||||
|
Note that the permutation iterator is not limited to strict
|
||||||
|
permutations of the given range V. The distance between begin and end
|
||||||
|
of the reindexing iterators is allowed to be smaller compared to the
|
||||||
|
size of the range V, in which case the permutation iterator only
|
||||||
|
provides a permutation of a subrange of V. The indexes neither need
|
||||||
|
to be unique. In this same context, it must be noted that the past the
|
||||||
|
end permutation iterator is completely defined by means of the
|
||||||
|
past-the-end iterator to the indices.
|
71
doc/permutation_iterator_eg.rst
Normal file
71
doc/permutation_iterator_eg.rst
Normal file
@ -0,0 +1,71 @@
|
|||||||
|
.. Copyright David Abrahams 2006. Distributed under the Boost
|
||||||
|
.. Software License, Version 1.0. (See accompanying
|
||||||
|
.. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
using namespace boost;
|
||||||
|
int i = 0;
|
||||||
|
|
||||||
|
typedef std::vector< int > element_range_type;
|
||||||
|
typedef std::list< int > index_type;
|
||||||
|
|
||||||
|
static const int element_range_size = 10;
|
||||||
|
static const int index_size = 4;
|
||||||
|
|
||||||
|
element_range_type elements( element_range_size );
|
||||||
|
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 );
|
||||||
|
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() );
|
||||||
|
|
||||||
|
typedef permutation_iterator< element_range_type::iterator, index_type::iterator > permutation_type;
|
||||||
|
permutation_type begin = make_permutation_iterator( elements.begin(), indices.begin() );
|
||||||
|
permutation_type it = begin;
|
||||||
|
permutation_type end = make_permutation_iterator( elements.begin(), indices.end() );
|
||||||
|
|
||||||
|
std::cout << "The original range is : ";
|
||||||
|
std::copy( elements.begin(), elements.end(), std::ostream_iterator< int >( std::cout, " " ) );
|
||||||
|
std::cout << "\n";
|
||||||
|
|
||||||
|
std::cout << "The reindexing scheme is : ";
|
||||||
|
std::copy( indices.begin(), indices.end(), std::ostream_iterator< int >( std::cout, " " ) );
|
||||||
|
std::cout << "\n";
|
||||||
|
|
||||||
|
std::cout << "The permutated range is : ";
|
||||||
|
std::copy( begin, end, std::ostream_iterator< int >( std::cout, " " ) );
|
||||||
|
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";
|
||||||
|
|
||||||
|
|
||||||
|
The output is::
|
||||||
|
|
||||||
|
The original range is : 0 1 2 3 4 5 6 7 8 9
|
||||||
|
The reindexing scheme is : 9 8 7 6
|
||||||
|
The permutated range is : 9 8 7 6
|
||||||
|
Elements at even indices in the permutation : 9 7
|
||||||
|
Permutation backwards : 6 7 8 9
|
||||||
|
Iterate backward with stride 2 : 6 8
|
||||||
|
|
||||||
|
|
||||||
|
The source code for this example can be found `here`__.
|
||||||
|
|
||||||
|
__ ../example/permutation_iter_example.cpp
|
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user