VTK  9.2.6
vtkSmartPointer.h
Go to the documentation of this file.
1 /*=========================================================================
2 
3  Program: Visualization Toolkit
4  Module: vtkSmartPointer.h
5 
6  Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen
7  All rights reserved.
8  See Copyright.txt or http://www.kitware.com/Copyright.htm for details.
9 
10  This software is distributed WITHOUT ANY WARRANTY; without even
11  the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
12  PURPOSE. See the above copyright notice for more information.
13 
14 =========================================================================*/
29 #ifndef vtkSmartPointer_h
30 #define vtkSmartPointer_h
31 
32 #include "vtkSmartPointerBase.h"
33 
34 #include "vtkMeta.h" // for IsComplete
35 #include "vtkNew.h" // for vtkNew.h
36 
37 #include <type_traits> // for is_base_of
38 #include <utility> // for std::move
39 
40 template <class T>
42 {
43  // These static asserts only fire when the function calling CheckTypes is
44  // used. Thus, this smart pointer class may still be used as a member variable
45  // with a forward declared T, so long as T is defined by the time the calling
46  // function is used.
47  template <typename U = T>
48  static void CheckTypes() noexcept
49  {
51  "vtkSmartPointer<T>'s T type has not been defined. Missing "
52  "include?");
54  "Cannot store an object with undefined type in "
55  "vtkSmartPointer. Missing include?");
56  static_assert(std::is_base_of<T, U>::value,
57  "Argument type is not compatible with vtkSmartPointer<T>'s "
58  "T type.");
60  "vtkSmartPointer can only be used with subclasses of "
61  "vtkObjectBase.");
62  }
63 
64 public:
68  vtkSmartPointer() noexcept
70  {
71  }
72 
78  // Need both overloads because the copy-constructor must be non-templated:
81  {
82  }
83 
84  template <class U>
87  {
88  vtkSmartPointer::CheckTypes<U>();
89  }
90  /* @} **/
91 
96  // Need both overloads because the move-constructor must be non-templated:
98  : vtkSmartPointerBase(std::move(r))
99  {
100  }
101 
102  template <class U>
104  : vtkSmartPointerBase(std::move(r))
105  {
106  vtkSmartPointer::CheckTypes<U>();
107  }
116  {
117  vtkSmartPointer::CheckTypes();
118  }
119 
120  template <typename U>
123  { // Create a new reference on copy
124  vtkSmartPointer::CheckTypes<U>();
125  }
127 
132  template <typename U>
135  { // Steal the reference on move
136  vtkSmartPointer::CheckTypes<U>();
137 
138  r.Object = nullptr;
139  }
140 
142 
146  // Need this since the compiler won't recognize template functions as
147  // assignment operators.
149  {
151  return *this;
152  }
153 
154  template <class U>
156  {
157  vtkSmartPointer::CheckTypes<U>();
158 
160  return *this;
161  }
163 
168  template <typename U>
170  {
171  vtkSmartPointer::CheckTypes<U>();
172 
173  this->vtkSmartPointerBase::operator=(r.Object);
174  return *this;
175  }
176 
181  template <typename U>
183  {
184  vtkSmartPointer::CheckTypes<U>();
185 
187  return *this;
188  }
189 
191 
194  T* GetPointer() const noexcept { return static_cast<T*>(this->Object); }
195  T* Get() const noexcept { return static_cast<T*>(this->Object); }
197 
201  operator T*() const noexcept { return static_cast<T*>(this->Object); }
202 
207  T& operator*() const noexcept { return *static_cast<T*>(this->Object); }
208 
212  T* operator->() const noexcept { return static_cast<T*>(this->Object); }
213 
226  void TakeReference(T* t) { *this = vtkSmartPointer<T>(t, NoReference()); }
227 
231  static vtkSmartPointer<T> New() { return vtkSmartPointer<T>(T::New(), NoReference()); }
238  {
239  return vtkSmartPointer<T>(T::ExtendedNew(), NoReference());
240  }
241 
246  {
247  return vtkSmartPointer<T>(t->NewInstance(), NoReference());
248  }
249 
263  static vtkSmartPointer<T> Take(T* t) { return vtkSmartPointer<T>(t, NoReference()); }
264 
265  // Work-around for HP and IBM overload resolution bug. Since
266  // NullPointerOnly is a private type the only pointer value that can
267  // be passed by user code is a null pointer. This operator will be
268  // chosen by the compiler when comparing against null explicitly and
269  // avoid the bogus ambiguous overload error.
270 #if defined(__HP_aCC) || defined(__IBMCPP__)
271 #define VTK_SMART_POINTER_DEFINE_OPERATOR_WORKAROUND(op) \
272  bool operator op(NullPointerOnly*) const { return ::operator op(*this, 0); }
273 
274 private:
275  class NullPointerOnly
276  {
277  };
278 
279 public:
280  VTK_SMART_POINTER_DEFINE_OPERATOR_WORKAROUND(==)
281  VTK_SMART_POINTER_DEFINE_OPERATOR_WORKAROUND(!=)
282  VTK_SMART_POINTER_DEFINE_OPERATOR_WORKAROUND(<)
283  VTK_SMART_POINTER_DEFINE_OPERATOR_WORKAROUND(<=)
284  VTK_SMART_POINTER_DEFINE_OPERATOR_WORKAROUND(>)
285  VTK_SMART_POINTER_DEFINE_OPERATOR_WORKAROUND(>=)
286 #undef VTK_SMART_POINTER_DEFINE_OPERATOR_WORKAROUND
287 #endif
288 protected:
289  vtkSmartPointer(T* r, const NoReference& n)
290  : vtkSmartPointerBase(r, n)
291  {
292  }
293 
294 private:
295  // These are purposely not implemented to prevent callers from
296  // trying to take references from other smart pointers.
297  void TakeReference(const vtkSmartPointerBase&) = delete;
298  static void Take(const vtkSmartPointerBase&) = delete;
299 };
300 
301 #define VTK_SMART_POINTER_DEFINE_OPERATOR(op) \
302  template <class T, class U> \
303  inline bool operator op(const vtkSmartPointer<T>& l, const vtkSmartPointer<U>& r) \
304  { \
305  return (l.GetPointer() op r.GetPointer()); \
306  } \
307  template <class T, class U> \
308  inline bool operator op(T* l, const vtkSmartPointer<U>& r) \
309  { \
310  return (l op r.GetPointer()); \
311  } \
312  template <class T, class U> \
313  inline bool operator op(const vtkSmartPointer<T>& l, U* r) \
314  { \
315  return (l.GetPointer() op r); \
316  } \
317  template <class T, class U> \
318  inline bool operator op(const vtkNew<T>& l, const vtkSmartPointer<U>& r) \
319  { \
320  return (l.GetPointer() op r.GetPointer()); \
321  } \
322  template <class T, class U> \
323  inline bool operator op(const vtkSmartPointer<T>& l, const vtkNew<U>& r) \
324  { \
325  return (l.GetPointer() op r.GetPointer); \
326  }
327 
337 
338 #undef VTK_SMART_POINTER_DEFINE_OPERATOR
339 
340 namespace vtk
341 {
342 
345 template <typename T>
347 {
348  return vtkSmartPointer<T>{ obj };
349 }
350 
353 template <typename T>
355 {
356  return vtkSmartPointer<T>::Take(obj);
357 }
358 
359 } // end namespace vtk
360 
364 template <class T>
365 inline ostream& operator<<(ostream& os, const vtkSmartPointer<T>& p)
366 {
367  return os << static_cast<const vtkSmartPointerBase&>(p);
368 }
369 
370 #endif
371 // VTK-HeaderTest-Exclude: vtkSmartPointer.h
static vtkSmartPointer< T > Take(T *t)
Transfer ownership of one reference to the given VTK object to a new smart pointer.
static vtkSmartPointer< T > NewInstance(T *t)
Create a new instance of the given VTK object.
vtkSmartPointer(const vtkNew< U > &r)
Initialize smart pointer to given object.
#define VTK_SMART_POINTER_DEFINE_OPERATOR(op)
vtkSmartPointerBase & operator=(vtkObjectBase *r)
Assign object to reference.
vtkSmartPointer(T *r, const NoReference &n)
vtkSmartPointer(vtkSmartPointer< U > &&r) noexcept
Initialize smart pointer with a new reference to the same object referenced by given smart pointer...
Hold a reference to a vtkObjectBase instance.
Definition: vtkMeta.h:32
Specialization of tuple ranges and iterators for vtkAOSDataArrayTemplate.
vtkSmartPointer & operator=(U *r)
Assign object to reference.
static vtkSmartPointer< T > New()
Create an instance of a VTK object.
vtkSmartPointer(const vtkSmartPointer &r)
Initialize smart pointer with a new reference to the same object referenced by given smart pointer...
This file contains a variety of metaprogramming constructs for working with vtk types.
T * operator->() const noexcept
Provides normal pointer target member access using operator ->.
T * Get() const noexcept
Get the contained pointer.
vtkSmartPointer & operator=(const vtkSmartPointer< U > &r)
Assign object to reference.
vtkSmartPointer(vtkNew< U > &&r) noexcept
Move the pointer from the vtkNew smart pointer to the new vtkSmartPointer, stealing its reference and...
vtkSmartPointer(vtkSmartPointer &&r) noexcept
Move the contents of r into this.
vtkSmartPointer(T *r)
Initialize smart pointer to given object.
vtkSmartPointer & operator=(const vtkNew< U > &r)
Assign object to reference.
static vtkSmartPointer< T > ExtendedNew()
Create an instance of a VTK object in a memkind extended memory space.
Non-templated superclass for vtkSmartPointer.
vtkSmartPointer() noexcept
Initialize smart pointer to nullptr.
vtkObjectBase * Object
void TakeReference(T *t)
Transfer ownership of one reference to the given VTK object to this smart pointer.
vtkSmartPointer< T > TakeSmartPointer(T *obj)
Construct a vtkSmartPointer containing obj.
vtkSmartPointer & operator=(const vtkSmartPointer &r)
Assign object to reference.
T & operator*() const noexcept
Dereference the pointer and return a reference to the contained object.
Allocate and hold a VTK object.
Definition: vtkMeta.h:30
vtkSmartPointer(const vtkSmartPointer< U > &r)
Initialize smart pointer with a new reference to the same object referenced by given smart pointer...
T * GetPointer() const noexcept
Get the contained pointer.
vtkSmartPointer< T > MakeSmartPointer(T *obj)
Construct a vtkSmartPointer containing obj.