diff options
Diffstat (limited to 'libodb/odb/object-result.hxx')
-rw-r--r-- | libodb/odb/object-result.hxx | 164 |
1 files changed, 164 insertions, 0 deletions
diff --git a/libodb/odb/object-result.hxx b/libodb/odb/object-result.hxx new file mode 100644 index 0000000..056d518 --- /dev/null +++ b/libodb/odb/object-result.hxx @@ -0,0 +1,164 @@ +// file : odb/object-result.hxx +// license : GNU GPL v2; see accompanying LICENSE file + +#ifndef ODB_OBJECT_RESULT_HXX +#define ODB_OBJECT_RESULT_HXX + +#include <odb/pre.hxx> + +#include <cstddef> // std::ptrdiff_t +#include <iterator> // iterator categories + +#include <odb/forward.hxx> +#include <odb/traits.hxx> +#include <odb/result.hxx> +#include <odb/pointer-traits.hxx> + +namespace odb +{ + // + // object_result_impl + // + template <typename T> + class object_result_impl; + + template <typename T> + class polymorphic_object_result_impl; + + template <typename T> + class no_id_object_result_impl; + + // + // object_result_impl_selector + // + template <typename T, + typename ID = typename object_traits<T>::id_type, + bool polymorphic = object_traits<T>::polymorphic> + struct object_result_impl_selector; + + template <typename T, typename ID> + struct object_result_impl_selector<T, ID, false> + { + typedef object_result_impl<T> type; + }; + + template <typename T, typename ID> + struct object_result_impl_selector<T, ID, true> + { + typedef polymorphic_object_result_impl<T> type; + }; + + template <typename T> + struct object_result_impl_selector<T, void, false> + { + typedef no_id_object_result_impl<T> type; + }; + + // + // result_iterator + // + + template <typename T, typename ID, bool polymorphic> + class object_result_iterator; + + template <typename T> + class result_iterator<T, class_object>: public object_result_iterator< + T, + typename object_traits<T>::id_type, + object_traits<T>::polymorphic> + { + public: + typedef T value_type; + typedef value_type& reference; + typedef value_type* pointer; + typedef std::ptrdiff_t difference_type; + typedef std::input_iterator_tag iterator_category; + + // T can be const T while object_type is always non-const. + // + typedef + object_result_iterator<T, + typename object_traits<T>::id_type, + object_traits<T>::polymorphic> base_type; + + public: + explicit + result_iterator (typename base_type::result_impl_type* res = 0) + : base_type (res) + { + } + + // Input iterator requirements. + // + public: + reference + operator* () const + { + return pointer_traits::get_ref (this->res_->current ()); + } + + // Our value_type is already a pointer so return it instead of + // a pointer to it (operator-> will just have to go one deeper + // in the latter case). + // + pointer + operator-> () const + { + return pointer_traits::get_ptr (this->res_->current ()); + } + + result_iterator& + operator++ () + { + this->res_->next (); + return *this; + } + + result_iterator + operator++ (int) + { + // All non-end iterators for a result object move together. + // + this->res_->next (); + return *this; + } + + public: + bool + equal (result_iterator j) const + { + return (this->res_ ? this->res_->end () : true) == + (j.res_ ? j.res_->end () : true); + } + + private: + // Use unrestricted pointer traits since that's what is returned by + // result_impl. + // + typedef + odb::pointer_traits< + typename object_traits< + typename base_type::object_type>::pointer_type> + pointer_traits; + }; + + // + // + template <typename T> + class result_base<T, class_object> + { + public: + typedef typename object_traits<T>::pointer_type value_type; + + // T can be const T while object_type is always non-const. + // + typedef typename object_traits<T>::object_type object_type; + typedef + typename object_result_impl_selector<object_type>::type + result_impl_type; + }; +} + +#include <odb/post.hxx> + +#endif // ODB_OBJECT_RESULT_HXX |