Arcane  v3.14.10.0
Documentation utilisateur
Chargement...
Recherche...
Aucune correspondance
SharedPtr.h
1// -*- tab-width: 2; indent-tabs-mode: nil; coding: utf-8-with-signature -*-
2//-----------------------------------------------------------------------------
3// Copyright 2000-2022 CEA (www.cea.fr) IFPEN (www.ifpenergiesnouvelles.com)
4// See the top-level COPYRIGHT file for details.
5// SPDX-License-Identifier: Apache-2.0
6//-----------------------------------------------------------------------------
7/*---------------------------------------------------------------------------*/
8/* SharedPtr.h (C) 2000-2022 */
9/* */
10/* Encapsulation d'un pointeur avec compteur de référence. */
11/*---------------------------------------------------------------------------*/
12#ifndef ARCANE_UTILS_SHAREDPTR_H
13#define ARCANE_UTILS_SHAREDPTR_H
14/*---------------------------------------------------------------------------*/
15/*---------------------------------------------------------------------------*/
16
17#include "arcane/utils/Ptr.h"
18#include "arcane/utils/Atomic.h"
19
20#include <iostream>
21#include <atomic>
22
23/*
24 * Différent de AutoRef où le pointeur doit référencer un objet satisfaisant
25 * un contrat d'utilisation similaire à l'interface ISharedReference
26 * (autre implémentation : std::(tr1::)|boost::shared_ptr
27 */
28
29/*---------------------------------------------------------------------------*/
30/*---------------------------------------------------------------------------*/
31
32namespace Arcane
33{
34
35/*---------------------------------------------------------------------------*/
36/*---------------------------------------------------------------------------*/
37
39{
40 public:
41
43 : m_counter(1)
44 {}
45 void addRef() { ++m_counter; }
46 void removeRef() { --m_counter; }
47 Int32 refCount() const { return m_counter.load(); }
48
49 private:
50
51 std::atomic<Int32> m_counter;
52};
53
54template <typename T>
55class SharedPtrT : public PtrT<T>
56{
57 private:
58
59 typedef PtrT<T> BaseClass;
60
61 public:
62
63 ~SharedPtrT() { reset(); }
64
66 : BaseClass(0)
67 , m_counter(0)
68 , m_free(true)
69 {}
70
71 //Constructeur de copie
72 SharedPtrT(const SharedPtrT<T>& ptr)
73 : PtrT<T>(0)
74 {
75 _copy(ptr.get(), ptr.refCountPtr(), ptr.explicitDelete());
76 }
77
78 // N'est pas utilise quand T2 = T
79 template <typename T2>
80 SharedPtrT(const SharedPtrT<T2>& ptr)
81 : PtrT<T>(0)
82 {
83 _copy(ptr.get(), ptr.refCountPtr(), ptr.explicitDelete());
84 }
85
86 // Constructeurs explicites
87 template <typename T2>
88 explicit SharedPtrT(T2* t, bool tofree = true)
89 : BaseClass(t)
90 , m_counter(new RefCounter())
91 , m_free(tofree)
92 {}
93
94 // Constructeurs pour faire un "dynamic_cast"
95 template <typename T2>
96 explicit SharedPtrT(const SharedPtrT<T2>& ptr, bool)
97 {
98 _copy(dynamic_cast<T*>(ptr.get()), ptr.refCountPtr(), ptr.explicitDelete());
99 }
100
101 SharedPtrT<T>& operator=(const SharedPtrT<T>& ptr)
102 {
103 reset();
104 _copy(ptr.get(), ptr.refCountPtr(), ptr.explicitDelete());
105 return (*this);
106 }
107
108 // N'est pas utilise quand T2 = T
109 template <typename T2>
110 SharedPtrT<T>& operator=(const SharedPtrT<T2>& ptr)
111 {
112 reset();
113 _copy(ptr.get(), ptr.refCountPtr(), ptr.explicitDelete());
114 return (*this);
115 }
116
117 bool isUnique() const { return (m_counter->refCount() == 1); }
118 Int32 refCount() const { return (m_counter) ? m_counter->refCount() : 0; }
119 bool isUsed() const { return (m_counter != NULL); }
120 void reset()
121 {
122 if (!m_counter)
123 return;
124 m_counter->removeRef();
125 if (m_counter->refCount() == 0) {
126 if (m_free)
127 delete BaseClass::m_value;
128 delete m_counter;
129 }
130 m_counter = 0;
131 BaseClass::m_value = 0;
132 }
133
134 RefCounter* refCountPtr() const { return m_counter; }
135 bool explicitDelete() const { return m_free; }
136
137 private:
138
139 void _copy(T* ptr, RefCounter* ref, bool free)
140 {
141 BaseClass::operator=(ptr);
142 m_counter = ref;
143 m_free = free;
144 if (m_counter != 0)
145 m_counter->addRef();
146 }
147
148 RefCounter* m_counter;
149 bool m_free;
150};
151
152/*---------------------------------------------------------------------------*/
153/*---------------------------------------------------------------------------*/
154
155template <typename T>
156SharedPtrT<T> SPtr(T* ptr)
157{
158 return SharedPtrT<T>(ptr);
159}
160
161template <typename T2, typename T>
162SharedPtrT<T2> SPtr_dynamic_cast(const SharedPtrT<T>& src)
163{
164 return SharedPtrT<T2>(src, true);
165}
166
167/*---------------------------------------------------------------------------*/
168/*---------------------------------------------------------------------------*/
169
170} // namespace Arcane
171
172/*---------------------------------------------------------------------------*/
173/*---------------------------------------------------------------------------*/
174
175#endif
Encapsulation d'un pointeur.
Definition Ptr.h:45
T * get() const
Retourne l'objet référé par l'instance.
Definition Ptr.h:121
-*- tab-width: 2; indent-tabs-mode: nil; coding: utf-8-with-signature -*-