diff --git a/include/boost/iterator_categories.hpp b/include/boost/iterator_categories.hpp new file mode 100644 index 0000000..138a5be --- /dev/null +++ b/include/boost/iterator_categories.hpp @@ -0,0 +1,159 @@ +#ifndef BOOST_ITERATOR_CATEGORIES_HPP +#define BOOST_ITERATOR_CATEGORIES_HPP + +#include +#include +#include +#include +#include + +namespace boost { + + // Return Type Categories + struct readable_iterator_tag { }; + struct writable_iterator_tag { }; + struct swappable_iterator_tag { }; + struct mutable_lvalue_iterator_tag : + virtual public writable_iterator_tag, + virtual public readable_iterator_tag { }; + struct constant_lvalue_iterator_tag : + virtual public readable_iterator_tag { }; + + // Traversal Categories + struct forward_traversal_tag { }; + struct bidirectional_traversal_tag : public forward_traversal_tag { }; + struct random_access_traversal_tag : public bidirectional_traversal_tag { }; + + struct error_iterator_tag { }; + + // Inherit from iterator_base if your iterator defines its own + // return_category and traversal_category. Otherwise, the "old style" + // iterator category will be mapped to the return_category and + // traversal_category. + struct new_iterator_base { }; + + namespace detail { + + struct return_category_from_nested_type { + template struct bind { + typedef typename Iterator::return_category type; + }; + }; + + struct traversal_category_from_nested_type { + template struct bind { + typedef typename Iterator::traversal_category type; + }; + }; + + template + struct choose_lvalue_return { + typedef typename ct_if::value, + boost::constant_lvalue_iterator_tag, + boost::mutable_lvalue_iterator_tag>::type type; + }; + + + template + struct iter_category_to_return { + typedef typename ct_if< + is_convertible::value, + typename choose_lvalue_return::type, + typename ct_if< + is_convertible::value, + boost::readable_iterator_tag, + typename ct_if< + is_convertible::value, + boost::writable_iterator_tag, + boost::error_iterator_tag + >::type + >::type + >::type type; + }; + + template + struct iter_category_to_traversal { + typedef typename ct_if< + is_convertible::value, + random_access_traversal_tag, + typename ct_if< + is_convertible::value, + bidirectional_traversal_tag, + forward_traversal_tag + >::type + >::type type; + }; + + struct return_category_from_old_traits { + template class bind { + typedef boost::detail::iterator_traits OldTraits; + typedef typename OldTraits::iterator_category Cat; + typedef typename OldTraits::value_type value_type; + public: + typedef iter_category_to_return::type type; + }; + }; + + struct traversal_category_from_old_traits { + template class bind { + typedef boost::detail::iterator_traits OldTraits; + typedef typename OldTraits::iterator_category Cat; + public: + typedef iter_category_to_traversal::type type; + }; + }; + + template + class choose_return_category { + typedef typename ct_if::value, + return_category_from_nested_type, + return_category_from_old_traits>::type Choice; + public: + typedef typename Choice:: template bind::type type; + }; + + template + class choose_traversal_category { + typedef typename ct_if::value, + traversal_category_from_nested_type, + traversal_category_from_old_traits>::type Choice; + public: + typedef typename Choice:: template bind::type type; + }; + + } // namespace detail + + template + struct return_category { + typedef typename detail::choose_return_category::type type; + }; + + + template + struct traversal_category { + typedef typename detail::choose_traversal_category::type type; + }; + +#if !defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION) + + template + struct return_category + { + typedef typename ct_if::value, + constant_lvalue_iterator_tag, + mutable_lvalue_iterator_tag>::type type; + }; + + template + struct traversal_category + { + typedef random_access_traversal_tag type; + }; + +#endif + +} // namespace boost + +#endif // BOOST_ITERATOR_CATEGORIES_HPP diff --git a/include/boost/iterator_concepts.hpp b/include/boost/iterator_concepts.hpp new file mode 100644 index 0000000..a30ff17 --- /dev/null +++ b/include/boost/iterator_concepts.hpp @@ -0,0 +1,172 @@ +#ifndef BOOST_ITERATOR_CONCEPTS_HPP +#define BOOST_ITERATOR_CONCEPTS_HPP + +#include +#include +#include +#include + +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. + + + //=========================================================================== + // Iterator Access Concepts + + template + class ReadableIteratorConcept { + public: + typedef typename std::iterator_traits::value_type value_type; + typedef typename std::iterator_traits::reference reference; + typedef typename boost::return_category::type return_category; + + void constraints() { + boost::function_requires< boost::SGIAssignableConcept >(); + boost::function_requires< boost::EqualityComparableConcept >(); + boost::function_requires< + boost::DefaultConstructibleConcept >(); + + BOOST_STATIC_ASSERT((boost::is_convertible::value)); + + reference r = *i; // or perhaps read(x) + value_type v(r); + boost::ignore_unused_variable_warning(v); + } + Iterator i; + }; + + template + class WritableIteratorConcept { + public: + typedef typename boost::return_category::type return_category; + + void constraints() { + boost::function_requires< boost::SGIAssignableConcept >(); + boost::function_requires< boost::EqualityComparableConcept >(); + boost::function_requires< + boost::DefaultConstructibleConcept >(); + + BOOST_STATIC_ASSERT((boost::is_convertible::value)); + + *i = v; // a good alternative could be something like write(x, v) + } + ValueType v; + Iterator i; + }; + + template + class ConstantLvalueIteratorConcept { + public: + typedef typename std::iterator_traits::value_type value_type; + typedef typename std::iterator_traits::reference reference; + typedef typename boost::return_category::type return_category; + + void constraints() { + boost::function_requires< ReadableIteratorConcept >(); + + BOOST_STATIC_ASSERT((boost::is_convertible::value)); + + BOOST_STATIC_ASSERT((boost::is_same::value)); + + reference v = *i; + boost::ignore_unused_variable_warning(v); + } + Iterator i; + }; + + template + class MutableLvalueIteratorConcept { + public: + typedef typename std::iterator_traits::value_type value_type; + typedef typename std::iterator_traits::reference reference; + typedef typename boost::return_category::type return_category; + + void constraints() { + boost::function_requires< ReadableIteratorConcept >(); + boost::function_requires< + WritableIteratorConcept >(); + + BOOST_STATIC_ASSERT((boost::is_convertible::value)); + + BOOST_STATIC_ASSERT((boost::is_same::value)); + + reference v = *i; + boost::ignore_unused_variable_warning(v); + } + Iterator i; + }; + + //=========================================================================== + // Iterator Traversal Concepts + + template + class ForwardIteratorConcept { + public: + typedef typename boost::traversal_category::type traversal_category; + + void constraints() { + boost::function_requires< boost::SGIAssignableConcept >(); + boost::function_requires< boost::EqualityComparableConcept >(); + boost::function_requires< + boost::DefaultConstructibleConcept >(); + + BOOST_STATIC_ASSERT((boost::is_convertible::value)); + ++i; + (void)i++; + } + Iterator i; + }; + + template + class BidirectionalIteratorConcept { + public: + typedef typename boost::traversal_category::type traversal_category; + + void constraints() { + boost::function_requires< ForwardIteratorConcept >(); + + BOOST_STATIC_ASSERT((boost::is_convertible::value)); + + --i; + (void)i--; + } + Iterator i; + }; + + template + class RandomAccessIteratorConcept { + public: + typedef typename boost::traversal_category::type traversal_category; + typedef typename std::iterator_traits::difference_type + difference_type; + + void constraints() { + boost::function_requires< BidirectionalIteratorConcept >(); + + BOOST_STATIC_ASSERT((boost::is_convertible::value)); + + i += n; + i = i + n; + i = n + i; + i -= n; + i = i - n; + n = i - j; + } + difference_type n; + Iterator i, j; + }; + +} // namespace boost_concepts + + +#endif // BOOST_ITERATOR_CONCEPTS_HPP