1 // Copyright David Abrahams 2002.
2 // Distributed under the Boost Software License, Version 1.0. (See
3 // accompanying file LICENSE_1_0.txt or copy at
4 // http://www.boost.org/LICENSE_1_0.txt)
5 #ifndef OBJECT_SLICES_DWA2002615_HPP
6 # define OBJECT_SLICES_DWA2002615_HPP
7 
8 # include <boost/python/detail/prefix.hpp>
9 
10 # include <boost/python/proxy.hpp>
11 # include <boost/python/object_core.hpp>
12 # include <boost/python/object_protocol.hpp>
13 # include <boost/python/handle.hpp>
14 # include <utility>
15 
16 namespace boost { namespace python { namespace api {
17 
18 struct const_slice_policies
19 {
20     typedef std::pair<handle<>, handle<> > key_type;
21     static object get(object const& target, key_type const& key);
22 };
23 
24 struct slice_policies : const_slice_policies
25 {
26     static object const& set(object const& target, key_type const& key, object const& value);
27     static void del(object const& target, key_type const& key);
28 };
29 
30 template <class T, class U>
slice_key(T x,U y)31 inline slice_policies::key_type slice_key(T x, U y)
32 {
33     return slice_policies::key_type(handle<>(x), handle<>(y));
34 }
35 
36 //
37 // implementation
38 //
39 template <class U>
40 object_slice
slice(object_cref start,object_cref finish)41 object_operators<U>::slice(object_cref start, object_cref finish)
42 {
43     object_cref2 x = *static_cast<U*>(this);
44     return object_slice(x, api::slice_key(borrowed(start.ptr()), borrowed(finish.ptr())));
45 }
46 
47 template <class U>
48 const_object_slice
slice(object_cref start,object_cref finish) const49 object_operators<U>::slice(object_cref start, object_cref finish) const
50 {
51     object_cref2 x = *static_cast<U const*>(this);
52     return const_object_slice(x, api::slice_key(borrowed(start.ptr()), borrowed(finish.ptr())));
53 }
54 
55 template <class U>
56 object_slice
slice(slice_nil,object_cref finish)57 object_operators<U>::slice(slice_nil, object_cref finish)
58 {
59     object_cref2 x = *static_cast<U*>(this);
60     return object_slice(x, api::slice_key(allow_null((PyObject*)0), borrowed(finish.ptr())));
61 }
62 
63 template <class U>
64 const_object_slice
slice(slice_nil,object_cref finish) const65 object_operators<U>::slice(slice_nil, object_cref finish) const
66 {
67     object_cref2 x = *static_cast<U const*>(this);
68     return const_object_slice(x, api::slice_key(allow_null((PyObject*)0), borrowed(finish.ptr())));
69 }
70 
71 template <class U>
72 object_slice
slice(slice_nil,slice_nil)73 object_operators<U>::slice(slice_nil, slice_nil)
74 {
75     object_cref2 x = *static_cast<U*>(this);
76     return object_slice(x, api::slice_key(allow_null((PyObject*)0), allow_null((PyObject*)0)));
77 }
78 
79 template <class U>
80 const_object_slice
slice(slice_nil,slice_nil) const81 object_operators<U>::slice(slice_nil, slice_nil) const
82 {
83     object_cref2 x = *static_cast<U const*>(this);
84     return const_object_slice(x, api::slice_key(allow_null((PyObject*)0), allow_null((PyObject*)0)));
85 }
86 
87 template <class U>
88 object_slice
slice(object_cref start,slice_nil)89 object_operators<U>::slice(object_cref start, slice_nil)
90 {
91     object_cref2 x = *static_cast<U*>(this);
92     return object_slice(x, api::slice_key(borrowed(start.ptr()), allow_null((PyObject*)0)));
93 }
94 
95 template <class U>
96 const_object_slice
slice(object_cref start,slice_nil) const97 object_operators<U>::slice(object_cref start, slice_nil) const
98 {
99     object_cref2 x = *static_cast<U const*>(this);
100     return const_object_slice(x, api::slice_key(borrowed(start.ptr()), allow_null((PyObject*)0)));
101 }
102 
103 template <class U>
104 template <class T, class V>
105 inline const_object_slice
slice(T const & start,V const & end) const106 object_operators<U>::slice(T const& start, V const& end) const
107 {
108     return this->slice(
109         typename slice_bound<T>::type(start)
110         , typename slice_bound<V>::type(end));
111 }
112 
113 template <class U>
114 template <class T, class V>
115 inline object_slice
slice(T const & start,V const & end)116 object_operators<U>::slice(T const& start, V const& end)
117 {
118     return this->slice(
119         typename slice_bound<T>::type(start)
120         , typename slice_bound<V>::type(end));
121 }
122 
get(object const & target,key_type const & key)123 inline object const_slice_policies::get(object const& target, key_type const& key)
124 {
125     return getslice(target, key.first, key.second);
126 }
127 
set(object const & target,key_type const & key,object const & value)128 inline object const& slice_policies::set(
129     object const& target
130     , key_type const& key
131     , object const& value)
132 {
133     setslice(target, key.first, key.second, value);
134     return value;
135 }
136 
del(object const & target,key_type const & key)137 inline void slice_policies::del(
138     object const& target
139     , key_type const& key)
140 {
141     delslice(target, key.first, key.second);
142 }
143 
144 }}} // namespace boost::python::api
145 
146 #endif // OBJECT_SLICES_DWA2002615_HPP
147