ClonedPtr.h
1 /* Copyright (C) 2012-2020 IBM Corp.
2  * This program is Licensed under the Apache License, Version 2.0
3  * (the "License"); you may not use this file except in compliance
4  * with the License. You may obtain a copy of the License at
5  * http://www.apache.org/licenses/LICENSE-2.0
6  * Unless required by applicable law or agreed to in writing, software
7  * distributed under the License is distributed on an "AS IS" BASIS,
8  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
9  * See the License for the specific language governing permissions and
10  * limitations under the License. See accompanying LICENSE file.
11  */
12 #ifndef HELIB_CLONEDPTR_H
13 #define HELIB_CLONEDPTR_H
14 
15 #include <utility> // std::swap
30 namespace helib {
31 
39 template <typename PTR>
40 PTR clonePtr(PTR& ptr)
41 {
42  static_assert(std::is_pointer<decltype(ptr->clone())>::value,
43  "`clone` method must return raw pointer.");
44 
45  return PTR(ptr->clone());
46 }
47 
53 template <typename T>
54 struct DeepCopy
55 {
61  static T* apply(const T* ptr)
62  {
63  static_assert(std::is_pointer<decltype(ptr->clone())>::value,
64  "`clone` method must return raw pointer.");
65 
66  return ptr->clone();
67  }
68 };
69 
75 template <typename T>
77 {
83  static T* apply(const T* ptr)
84  {
85  static_assert(std::is_copy_constructible<T>::value,
86  "Must be copy constructable.");
87 
88  return new T(*ptr);
89  }
90 };
91 
99 template <typename T, typename Cloner = DeepCopy<T>>
101 {
102 public:
106  using value_type = T;
107 
112  explicit ClonedPtr(T* p = nullptr) : ptr(p) {}
113 
118  ClonedPtr(std::nullptr_t) : ptr(nullptr) {}
119 
124  {
125  if (ptr != nullptr)
126  delete ptr;
127  }
128 
134  ClonedPtr(const ClonedPtr& other) : ptr(copy(other.ptr)) {}
135 
141  ClonedPtr(ClonedPtr&& other) noexcept : ptr{std::exchange(other.ptr, nullptr)}
142  {}
143 
151  {
152  if (this != &other) {
153  delete ptr;
154  ptr = copy(other.ptr);
155  }
156  return *this;
157  }
158 
165  ClonedPtr& operator=(ClonedPtr&& other) noexcept
166  {
167  if (this != &other) {
168  delete ptr;
169  ptr = std::exchange(other.ptr, nullptr);
170  }
171  return *this;
172  }
173 
180  void reset(T* p = nullptr)
181  {
182  if (ptr != p) {
183  if (ptr != nullptr)
184  delete ptr;
185  ptr = p;
186  }
187  }
188 
194  T* release() noexcept
195  {
196  T* ptr_to_release = ptr;
197  ptr = nullptr;
198  return ptr_to_release;
199  }
200 
205  explicit operator bool() const noexcept { return ptr != nullptr; }
206 
211  const T& operator*() const { return *ptr; }
212 
217  T& operator*() { return *ptr; }
218 
223  const T* operator->() const { return ptr; }
224 
229  T* operator->() { return ptr; }
230 
235  const T* get() const { return ptr; }
236 
241  T* get() { return ptr; }
242 
249  bool operator==(const ClonedPtr& other) const { return ptr == other.ptr; }
250 
257  bool operator!=(const ClonedPtr& other) const { return ptr != other.ptr; }
258 
265  bool operator<(const ClonedPtr& other) const { return ptr < other.ptr; }
266 
273  bool operator>(const ClonedPtr& other) const { return ptr > other.ptr; }
274 
281  bool operator<=(const ClonedPtr& other) const { return ptr <= other.ptr; }
282 
289  bool operator>=(const ClonedPtr& other) const { return ptr >= other.ptr; }
290 
296  void swap(ClonedPtr& other) { std::swap(ptr, other.ptr); }
297 
298 private:
299  // Copy function applies cloning policy.
300  T* copy(T* p) { return (p ? Cloner::apply(p) : nullptr); }
301 
302  // The raw pointer to the managed object.
303  T* ptr = nullptr;
304 };
305 
311 template <typename T>
313 
324 template <typename T, typename... Args>
326 {
327  return ClonedPtr<T>(new T(std::forward<Args>(args)...));
328 }
329 
330 } // namespace helib
331 
332 #endif // HELIB_CLONEDPTR_H
A smart pointer that clones the object it holds when it is copied.
Definition: ClonedPtr.h:101
ClonedPtr(T *p=nullptr)
Explicit constructor to create new ClonedPtr object.
Definition: ClonedPtr.h:112
T & operator*()
Dereference the smart pointer.
Definition: ClonedPtr.h:217
~ClonedPtr()
The destructor deletes the managed object.
Definition: ClonedPtr.h:123
ClonedPtr(const ClonedPtr &other)
Copy construct by cloning the managed object based on the cloning policy.
Definition: ClonedPtr.h:134
T * operator->()
Struct dereference to access members of the managed object.
Definition: ClonedPtr.h:229
const T * operator->() const
Struct dereference to access members of the managed object.
Definition: ClonedPtr.h:223
const T & operator*() const
Dereference the smart pointer.
Definition: ClonedPtr.h:211
T * release() noexcept
Release the ownership of the currently managed object by returning the pointer and setting the held p...
Definition: ClonedPtr.h:194
T value_type
The type of the managed object.
Definition: ClonedPtr.h:106
bool operator>(const ClonedPtr &other) const
Greater than another ClonedPtr object.
Definition: ClonedPtr.h:273
bool operator<=(const ClonedPtr &other) const
Less than or equal to another ClonedPtr object.
Definition: ClonedPtr.h:281
bool operator<(const ClonedPtr &other) const
Less than another ClonedPtr object.
Definition: ClonedPtr.h:265
void swap(ClonedPtr &other)
Swap the managed objects of the this ClonedPtr object and another.
Definition: ClonedPtr.h:296
T * get()
Get the pointer managed by ClonedPtr object.
Definition: ClonedPtr.h:241
ClonedPtr & operator=(ClonedPtr &&other) noexcept
Move construct by taking ownership of the managed object by the ClonedPtr object being moved and sett...
Definition: ClonedPtr.h:165
ClonedPtr & operator=(const ClonedPtr &other)
Copy assign by cloning the managed object based on the cloning policy.
Definition: ClonedPtr.h:150
bool operator==(const ClonedPtr &other) const
Equal to another ClonedPtr object.
Definition: ClonedPtr.h:249
bool operator>=(const ClonedPtr &other) const
Greater than or equal to another ClonedPtr object.
Definition: ClonedPtr.h:289
ClonedPtr(std::nullptr_t)
Special constructor to create new ClonedPtr object promoting a nullptr.
Definition: ClonedPtr.h:118
void reset(T *p=nullptr)
Reset method deletes the object that it currently managed and manages the object given by a raw point...
Definition: ClonedPtr.h:180
bool operator!=(const ClonedPtr &other) const
Not equal to another ClonedPtr object.
Definition: ClonedPtr.h:257
ClonedPtr(ClonedPtr &&other) noexcept
Move construct by taking ownership of the managed object by the ClonedPtr object being moved and sett...
Definition: ClonedPtr.h:141
const T * get() const
Get the pointer managed by ClonedPtr object.
Definition: ClonedPtr.h:235
Definition: apiAttributes.h:21
ClonedPtr< T > makeClonedPtr(Args &&... args)
Construct an object of type T based on arguments passed and point to it with a ClonedPtr object.
Definition: ClonedPtr.h:325
PTR clonePtr(PTR &ptr)
Clone any type of pointer.
Definition: ClonedPtr.h:40
Deep copy an object by using its clone method.
Definition: ClonedPtr.h:55
static T * apply(const T *ptr)
Apply the cloning policy.
Definition: ClonedPtr.h:61
Shallow copy an object by using its copy constructor.
Definition: ClonedPtr.h:77
static T * apply(const T *ptr)
Apply the cloning policy.
Definition: ClonedPtr.h:83