VTK  9.3.20240418
vtkWeakPointer.h
Go to the documentation of this file.
1 // SPDX-FileCopyrightText: Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen
2 // SPDX-License-Identifier: BSD-3-Clause
34 #ifndef vtkWeakPointer_h
35 #define vtkWeakPointer_h
36 
37 #include "vtkWeakPointerBase.h"
38 
39 #include "vtkMeta.h" // for IsComplete
40 #include "vtkNew.h" // for vtkNew
41 
42 #include <type_traits> // for is_base_of
43 #include <utility> // for std::move
44 
45 VTK_ABI_NAMESPACE_BEGIN
46 template <class T>
48 {
49  // These static asserts only fire when the function calling CheckTypes is
50  // used. Thus, this smart pointer class may still be used as a member variable
51  // with a forward declared T, so long as T is defined by the time the calling
52  // function is used.
53  template <typename U = T>
54  static void CheckTypes() noexcept
55  {
57  "vtkWeakPointer<T>'s T type has not been defined. Missing "
58  "include?");
60  "Cannot store an object with undefined type in "
61  "vtkWeakPointer. Missing include?");
62  static_assert(std::is_base_of<T, U>::value,
63  "Argument type is not compatible with vtkWeakPointer<T>'s "
64  "T type.");
66  "vtkWeakPointer can only be used with subclasses of "
67  "vtkObjectBase.");
68  }
69 
70 public:
74  vtkWeakPointer() noexcept
76  {
77  }
78 
85  {
86  }
87 
88  template <class U>
91  {
92  vtkWeakPointer::CheckTypes<U>();
93  }
94  /* @} **/
95 
101  : vtkWeakPointerBase(std::move(r))
102  {
103  }
104 
105  template <class U>
107  : vtkWeakPointerBase(std::move(r))
108  {
109  vtkWeakPointer::CheckTypes<U>();
110  }
111  /* @} **/
112 
118  : vtkWeakPointerBase(r)
119  {
120  vtkWeakPointer::CheckTypes();
121  }
122 
123  template <typename U>
126  { // Create a new reference on copy
127  vtkWeakPointer::CheckTypes<U>();
128  }
130 
132 
136  {
138  return *this;
139  }
140 
141  template <class U>
143  {
144  vtkWeakPointer::CheckTypes<U>();
145 
147  return *this;
148  }
150 
152 
156  {
157  this->vtkWeakPointerBase::operator=(std::move(r));
158  return *this;
159  }
160 
161  template <class U>
163  {
164  vtkWeakPointer::CheckTypes<U>();
165 
166  this->vtkWeakPointerBase::operator=(std::move(r));
167  return *this;
168  }
170 
172 
176  {
177  vtkWeakPointer::CheckTypes();
179  return *this;
180  }
181 
182  template <typename U>
184  {
185  vtkWeakPointer::CheckTypes<U>();
186 
187  this->vtkWeakPointerBase::operator=(r.Object);
188  return *this;
189  }
191 
193 
196  T* GetPointer() const noexcept { return static_cast<T*>(this->Object); }
197  T* Get() const noexcept { return static_cast<T*>(this->Object); }
198  operator T*() const noexcept { return static_cast<T*>(this->Object); }
199 
204  T& operator*() const noexcept { return *static_cast<T*>(this->Object); }
205 
209  T* operator->() const noexcept { return static_cast<T*>(this->Object); }
210 
211  // Work-around for HP and IBM overload resolution bug. Since
212  // NullPointerOnly is a private type the only pointer value that can
213  // be passed by user code is a null pointer. This operator will be
214  // chosen by the compiler when comparing against null explicitly and
215  // avoid the bogus ambiguous overload error.
216 #if defined(__HP_aCC) || defined(__IBMCPP__)
217 #define VTK_WEAK_POINTER_DEFINE_OPERATOR_WORKAROUND(op) \
218  bool operator op(NullPointerOnly*) const { return ::operator op(*this, 0); }
219 
220 private:
221  class NullPointerOnly
222  {
223  };
224 
225 public:
226  VTK_WEAK_POINTER_DEFINE_OPERATOR_WORKAROUND(==)
227  VTK_WEAK_POINTER_DEFINE_OPERATOR_WORKAROUND(!=)
228  VTK_WEAK_POINTER_DEFINE_OPERATOR_WORKAROUND(<)
229  VTK_WEAK_POINTER_DEFINE_OPERATOR_WORKAROUND(<=)
230  VTK_WEAK_POINTER_DEFINE_OPERATOR_WORKAROUND(>)
231  VTK_WEAK_POINTER_DEFINE_OPERATOR_WORKAROUND(>=)
232 #undef VTK_WEAK_POINTER_DEFINE_OPERATOR_WORKAROUND
233 #endif
234 protected:
235  vtkWeakPointer(T* r, const NoReference& n)
236  : vtkWeakPointerBase(r, n)
237  {
238  }
239 
240 private:
241  // These are purposely not implemented to prevent callers from
242  // trying to take references from other smart pointers.
243  void TakeReference(const vtkWeakPointerBase&) = delete;
244  static void Take(const vtkWeakPointerBase&) = delete;
245 };
246 
247 #define VTK_WEAK_POINTER_DEFINE_OPERATOR(op) \
248  template <class T, class U> \
249  inline bool operator op(const vtkWeakPointer<T>& l, const vtkWeakPointer<U>& r) \
250  { \
251  return (l.GetPointer() op r.GetPointer()); \
252  } \
253  template <class T, class U> \
254  inline bool operator op(T* l, const vtkWeakPointer<U>& r) \
255  { \
256  return (l op r.GetPointer()); \
257  } \
258  template <class T, class U> \
259  inline bool operator op(const vtkWeakPointer<T>& l, U* r) \
260  { \
261  return (l.GetPointer() op r); \
262  } \
263  template <class T, class U> \
264  inline bool operator op(const vtkNew<T>& l, const vtkWeakPointer<U>& r) \
265  { \
266  return (l.GetPointer() op r.GetPointer()); \
267  } \
268  template <class T, class U> \
269  inline bool operator op(const vtkWeakPointer<T>& l, const vtkNew<U>& r) \
270  { \
271  return (l.GetPointer() op r.GetPointer); \
272  }
273 
283 
284 #undef VTK_WEAK_POINTER_DEFINE_OPERATOR
285 
286 VTK_ABI_NAMESPACE_END
287 
288 namespace vtk
289 {
290 VTK_ABI_NAMESPACE_BEGIN
291 
294 template <typename T>
296 {
297  return vtkWeakPointer<T>(obj);
298 }
299 
300 VTK_ABI_NAMESPACE_END
301 } // end namespace vtk
302 
303 VTK_ABI_NAMESPACE_BEGIN
307 template <class T>
308 inline ostream& operator<<(ostream& os, const vtkWeakPointer<T>& p)
309 {
310  return os << static_cast<const vtkWeakPointerBase&>(p);
311 }
312 
313 VTK_ABI_NAMESPACE_END
314 #endif
315 
316 // VTK-HeaderTest-Exclude: vtkWeakPointer.h
Allocate and hold a VTK object.
Definition: vtkNew.h:160
Non-templated superclass for vtkWeakPointer.
vtkWeakPointerBase & operator=(vtkObjectBase *r)
Assign object to reference.
vtkObjectBase * Object
vtkWeakPointerBase() noexcept
Initialize smart pointer to nullptr.
a weak reference to a vtkObject.
T & operator*() const noexcept
Dereference the pointer and return a reference to the contained object.
vtkWeakPointer & operator=(vtkWeakPointer< U > &&r) noexcept
Move r's object into this weak pointer, setting r to nullptr.
T * Get() const noexcept
Get the contained pointer.
vtkWeakPointer & operator=(const vtkWeakPointer< U > &r)
Assign object to reference.
vtkWeakPointer & operator=(vtkWeakPointer &&r) noexcept
Move r's object into this weak pointer, setting r to nullptr.
T * operator->() const noexcept
Provides normal pointer target member access using operator ->.
vtkWeakPointer(const vtkWeakPointer< U > &r)
Initialize smart pointer with the given smart pointer.
vtkWeakPointer() noexcept
Initialize smart pointer to nullptr.
vtkWeakPointer(vtkWeakPointer< U > &&r) noexcept
Initialize smart pointer with the given smart pointer.
vtkWeakPointer & operator=(const vtkWeakPointer &r)
Assign object to reference.
vtkWeakPointer & operator=(T *r)
Assign object to reference.
vtkWeakPointer(vtkWeakPointer &&r) noexcept
Move r's object into the new weak pointer, setting r to nullptr.
vtkWeakPointer & operator=(const vtkNew< U > &r)
Assign object to reference.
vtkWeakPointer(T *r, const NoReference &n)
Get the contained pointer.
vtkWeakPointer(const vtkWeakPointer &r)
Initialize smart pointer with the given smart pointer.
vtkWeakPointer(T *r)
Initialize smart pointer to given object.
T * GetPointer() const noexcept
Get the contained pointer.
vtkWeakPointer(const vtkNew< U > &r)
Initialize smart pointer with the given smart pointer.
@ value
Definition: vtkX3D.h:220
Specialization of tuple ranges and iterators for vtkAOSDataArrayTemplate.
vtkWeakPointer< T > TakeWeakPointer(T *obj)
Construct a vtkWeakPointer<T> containing obj.
This file contains a variety of metaprogramming constructs for working with vtk types.
#define VTK_WEAK_POINTER_DEFINE_OPERATOR(op)
ostream & operator<<(ostream &os, const vtkWeakPointer< T > &p)
Streaming operator to print smart pointer like regular pointers.