DGtal 1.3.0
Loading...
Searching...
No Matches
CountedConstPtrOrConstPtr.h
1
17#pragma once
18
33#if defined(CountedConstPtrOrConstPtr_RECURSES)
34#error Recursive header files inclusion detected in CountedConstPtrOrConstPtr.h
35#else // defined(CountedConstPtrOrConstPtr_RECURSES)
37#define CountedConstPtrOrConstPtr_RECURSES
38
39#if !defined CountedConstPtrOrConstPtr_h
41#define CountedConstPtrOrConstPtr_h
42
44// Inclusions
45#include <iostream>
46#include "DGtal/base/Common.h"
47#include "DGtal/base/CountedPtr.h"
48#include "DGtal/base/CountedPtrOrPtr.h"
50
51namespace DGtal
52{
53
55 // template class CountedConstPtrOrConstPtr
93 template <typename T>
95 {
96 public:
97
98 // ----------------------- Standard services ------------------------------
99 public:
100
103
119 inline explicit CountedConstPtrOrConstPtr( const T* p = 0, bool isCountedPtr = true )
120 : myAny(0), myIsCountedPtr( isCountedPtr )
121 {
122 if ( isCountedPtr ) {
123 if (p) myAny = static_cast<void*>( new Counter( const_cast<T*>( p ) ) );
124 }
125 else
126 myAny = const_cast<void*>( static_cast<const void*>( p ) );
127 }
128
136 {
137 if ( myIsCountedPtr ) release();
138 }
139
148 : myIsCountedPtr( true )
149 {
150 acquire( r.myCounter );
151 }
152
163 : myIsCountedPtr( r.myIsCountedPtr )
164 {
165 if ( myIsCountedPtr )
166 acquire( r.counterPtr() );
167 else
168 myAny = r.myAny;
169 }
170
181 : myIsCountedPtr( r.myIsCountedPtr )
182 {
183 if ( myIsCountedPtr )
184 acquire( r.counterPtr() );
185 else
186 myAny = r.myAny;
187 }
188
202 {
203 if ( this != & r ) {
204 if ( myIsCountedPtr ) release();
205 myIsCountedPtr = r.myIsCountedPtr;
206 if ( r.myIsCountedPtr ) acquire( r.counterPtr() );
207 else myAny = r.myAny;
208 }
209 return *this;
210 }
211
225 {
226 if ( myIsCountedPtr ) release();
227 myIsCountedPtr = r.myIsCountedPtr;
228 if ( r.myIsCountedPtr ) acquire( r.counterPtr() );
229 else myAny = r.myAny;
230 return *this;
231 }
232
244 {
245 if ( myIsCountedPtr ) release();
246 myIsCountedPtr = true;
247 acquire( r.myCounter );
248 return *this;
249 }
250
254 bool isSmart() const
255 {
256 return myIsCountedPtr;
257 }
258
262 bool isSimple() const
263 {
264 return ! myIsCountedPtr;
265 }
266
273 bool operator==( const T* other ) const
274 {
275 return myIsCountedPtr ? ( myAny ? counterPtr()->ptr : 0 ) == other : ptr() == other;
276 }
277
284 bool operator!=( const T* other ) const
285 {
286 return myIsCountedPtr ? ( myAny ? counterPtr()->ptr : 0 ) != other : ptr() != other;
287 }
288
297 const T& operator*() const noexcept
298 {
299 // Travis is too slow in Debug mode with this ASSERT.
300 ASSERT( isValid() );
301 return myIsCountedPtr ? ( * counterPtr()->ptr ) : ( * ptr() );
302 }
303
313 const T* operator->() const noexcept
314 {
315 // Travis is too slow in Debug mode with this ASSERT.
316 ASSERT( isValid() );
317 return myIsCountedPtr ? counterPtr()->ptr : ptr();
318 }
319
327 const T* get() const noexcept
328 {
329 return myIsCountedPtr ? ( myAny ? counterPtr()->ptr : 0 ) : ptr();
330 }
331
337 bool unique() const noexcept
338 {
339 return myIsCountedPtr
340 ? ( myAny ? counterPtr()->count == 1 : true )
341 : true;
342 }
343
351 unsigned int count() const
352 {
353 return myIsCountedPtr ? counterPtr()->count : 0;
354 }
355
366 inline const T* drop()
367 { // Gives back the pointer without deleting him. Delete only the counter.
368 ASSERT( isValid() );
369 if ( myIsCountedPtr ) {
370 ASSERT( unique() );
371 T* tmp = counterPtr()->ptr;
372 delete counterPtr();
373 myAny = 0;
374 return tmp;
375 } else {
376 return ptr();
377 }
378 }
379
380private:
381
384 void* myAny;
387
388
394 inline Counter* counterPtr() const
395 {
396 // Travis is too slow in Debug mode with this ASSERT.
397 ASSERT( myIsCountedPtr );
398 return static_cast<Counter*>( myAny );
399 }
400
406 inline T* ptr() const
407 {
408 // Travis is too slow in Debug mode with this ASSERT.
409 ASSERT( ! myIsCountedPtr );
410 return static_cast<T*>( myAny );
411 }
412
420 inline void acquire(Counter* c) noexcept
421 { // increment the count
422 // Travis is too slow in Debug mode with this ASSERT.
423 ASSERT( myIsCountedPtr );
424 myAny = static_cast<void*>( c );
425 if (c) ++c->count;
426 }
427
436 void release()
437 { // decrement the count, delete if it is 0
438 // Travis is too slow in Debug mode with this ASSERT.
439 ASSERT( myIsCountedPtr );
440 if (myAny) {
441 Counter * counter = counterPtr();
442 if (--counter->count == 0) {
443 delete counter->ptr;
444 delete counter;
445 }
446 myAny = 0;
447 }
448 }
449
450
451 // ----------------------- Interface --------------------------------------
452 public:
453
458 void selfDisplay ( std::ostream & out ) const;
459
464 bool isValid() const;
465
466 // ------------------------- Protected Datas ------------------------------
467 private:
468 // ------------------------- Private Datas --------------------------------
469 private:
470
471 // ------------------------- Hidden services ------------------------------
472 protected:
473
474
475 // ------------------------- Internals ------------------------------------
476 private:
477
478 }; // end of class CountedConstPtrOrConstPtr
479
480
487 template <typename T>
488 std::ostream&
489 operator<< ( std::ostream & out, const CountedConstPtrOrConstPtr<T> & object );
490
491} // namespace DGtal
492
493
495// Includes inline functions.
496#include "DGtal/base/CountedConstPtrOrConstPtr.ih"
497
498// //
500
501#endif // !defined CountedConstPtrOrConstPtr_h
502
503#undef CountedConstPtrOrConstPtr_RECURSES
504#endif // else defined(CountedConstPtrOrConstPtr_RECURSES)
Aim: Smart or simple const pointer on T. It can be a smart pointer based on reference counts or a sim...
CountedConstPtrOrConstPtr(const T *p=0, bool isCountedPtr=true)
CountedConstPtrOrConstPtr(const CountedPtrOrPtr< T > &r) noexcept
CountedConstPtrOrConstPtr(const CountedPtr< T > &r) noexcept
bool myIsCountedPtr
If true, 'this' pointer object is smart, otherwise it is simple.
CountedConstPtrOrConstPtr & operator=(const CountedPtr< T > &r)
CountedConstPtrOrConstPtr & operator=(const CountedPtrOrPtr< T > &r)
void selfDisplay(std::ostream &out) const
CountedConstPtrOrConstPtr(const CountedConstPtrOrConstPtr &r) noexcept
CountedConstPtrOrConstPtr & operator=(const CountedConstPtrOrConstPtr &r)
CountedPtr< T >::Counter Counter
The counter is the same as CountedPtr.
Aim: Smart or simple pointer on T. It can be a smart pointer based on reference counts or a simple po...
Aim: Smart pointer based on reference counts.
Definition: CountedPtr.h:80
DGtal is the top-level namespace which contains all DGtal functions and types.
std::ostream & operator<<(std::ostream &out, const ClosedIntegerHalfPlane< TSpace > &object)
T * ptr
A pointer to a (shared) dynamically allocated object of type T.
Definition: CountedPtr.h:105
unsigned count
The number of CountedPtr pointing to this counter.
Definition: CountedPtr.h:107