Loading...
Searching...
No Matches
Cloner.h
1/*
2
3MIT License
4
5Copyright (c) 2017 FMI Open Development / Markus Peura, first.last@fmi.fi
6
7Permission is hereby granted, free of charge, to any person obtaining a copy
8of this software and associated documentation files (the "Software"), to deal
9in the Software without restriction, including without limitation the rights
10to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
11copies of the Software, and to permit persons to whom the Software is
12furnished to do so, subject to the following conditions:
13
14The above copyright notice and this permission notice shall be included in all
15copies or substantial portions of the Software.
16
17THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
20AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
22OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
23SOFTWARE.
24
25*/
26/*
27Part of Rack development has been done in the BALTRAD projects part-financed
28by the European Union (European Regional Development Fund and European
29Neighbourhood Partnership Instrument, Baltic Sea Region Programme 2007-2013)
30*/
31#ifndef Cloner_H_
32#define Cloner_H_
33
34//#include <list>
35#include <map>
36#include <exception>
37#include <iostream>
38#include <sstream>
39
40namespace drain {
41
45template <class T>
46struct ClonerBase {
47
49
52 typedef size_t index_t;
53
54 // If
55 typedef std::pair<index_t, T*> entry_t;
56
57 ClonerBase(){};
58
59 virtual
61 };
62
63
64 virtual
65 T & getCloned() const = 0; // could be const (if mutable ptrs )
66
67 virtual
68 entry_t getClonerEntry() const = 0;
69
70
72 // virtual const T & getCloned(index_t i) const = 0;
73
75 virtual
76 T & getCloned(index_t i) const = 0;
77
78
80 virtual
81 const T & getSource() const = 0;
82
84 virtual
85 T & getSource() = 0;
86
87
88
89 // Return the number of cloned instances.
90 virtual
91 size_t count() const = 0;
92
94
97 virtual // clear
98 bool drop(index_t i) const = 0;
99
100
101 //experimental
102 // virtual bool dropUnique() = 0;
103
104 protected:
105
106
107
108};
109
110
112
117template <class B, class S>
118struct Cloner : public ClonerBase<B> {
119
121
122 // "inherit" a type
123 typedef typename clonerbase_t::index_t index_t;
124
125 // "inherit" a type
126 typedef typename clonerbase_t::entry_t entry_t;
127
128 typedef std::map<index_t,S *> ptr_container_t;
129
130
131 Cloner(){};
132
134 Cloner(const Cloner<B,S> & c) : src(c.src){
135 };
136
138 Cloner(const S & s) : src(s){
139 };
140
141 virtual
142 ~Cloner(){
143 for (typename ptr_container_t::iterator it=ptrs.begin(); it!= ptrs.end(); ++it){
144 //std::cerr << "deleting instance, id=" << it->first << '\n';
145 delete it->second;
146 }
147 };
148
150 B & getCloned() const {
151 return getClonedSrc();
152 };
153
154
156 /*
157 *
158 virtual
159 const B & getCloned(index_t i) const {
160 typename ptr_container_t::const_iterator it = ptrs.find(i);
161 if (it == ptrs.end()){
162 std::stringstream sstr;
163 sstr << __FILE__ << ':' << __FUNCTION__ << ": index not found: "<< i;
164 throw std::runtime_error(sstr.str());
165 }
166 return *it->second;
167 };
168 */
169
171 /*
172 * \param i - index (id) of the instance.
173 */
174 virtual
175 B & getCloned(index_t i) const {
176 typename ptr_container_t::iterator it = ptrs.find(i);
177 if (it == ptrs.end()){
178 std::stringstream sstr;
179 sstr << __FILE__ << ':' << __FUNCTION__ << ": index not found: "<< i;
180 throw std::runtime_error(sstr.str());
181 }
182 return *it->second;
183 };
184
185
187 S & getClonedSrc() const{
188 S *ptr = new S(src); // NOTE: parameterReferences must be done
189 //this->ptrs.insert(ptr); //push_front(p);
190 this->ptrs[getNewIndex()] = ptr;
191 return *ptr;
192 };
193
194
195 virtual
196 entry_t getClonerEntry() const {
197 S *ptr = new S(src); // NOTE: parameterReferences must be done
198 index_t i = getNewIndex();
199 this->ptrs[i] = ptr; //.insert(ptr); //push_front(p);
200 return entry_t(i, ptr);
201 };
202
203
204 /* Consider separating these to "Provider" or "Factory" etc. */
205
207 /*
208 * The returned object is possibly static.
209 */
210 virtual
211 const B & getSource() const {
212 return getSourceOrig();
213 };
214
216 /*
217 * The returned object is possibly static.
218 */
219 virtual
220 B & getSource() {
221 return getSourceOrig();
222 };
223
225 /*
226 * The returned object is possibly static.
227 */
228 virtual
229 const S & getSourceOrig() const {
230 return src;
231 };
232
234 /*
235 * The returned object is possibly static.
236 */
237 virtual
239 return src;
240 };
241
242
243 virtual inline
244 size_t count() const {
245 return ptrs.size();
246 }
247
248
250 virtual inline // clear
251 bool drop(index_t i) const override {
252
253 const typename ptr_container_t::iterator it = ptrs.find(i);
254
255 if (it != ptrs.end()){
256 // std::cout << "deleting " << *ptr << ", at #" << (long int)ptr << '\n';
257 // std::cout << "deleting " << (long int)ptr << '\n';
258 delete it->second;
259 ptrs.erase(it); // TODO!
260 return true;
261 }
262 else {
263 std::cerr << "already deleted or does not exist: " << i << '\n';
264 // warn?
265 return false;
266 }
267
268 }
269
270
271 //protected:
272
274 // static S entry; // Consider non-static
275 S src; // Consider non-static
276
278 /*
279 inline
280 void clear(){
281 for (typename ptr_container_t::iterator it=ptrs.begin(); it!= ptrs.end(); ++it){
282 S *ptr = *it;
283 std::cout << "deleting " << *ptr << ", at #" << (long int)ptr << '\n';
284 delete ptr;
285 }
286 ptrs.clear();
287 }
288 */
289
290
291
292protected:
293
294 // TODO: re-allocate empty slots
295 inline
296 index_t getNewIndex() const {
297 // pra gma omp critical
298 {
299 if (this->ptrs.empty())
300 return 1;
301 else {
302 // std::cerr << "getNewIndex: " << this->ptrs.rbegin()->first << '\n';
303 return this->ptrs.rbegin()->first + 1;
304 }
305 }
306 }
307
308 // Structure for storing pointers until the target objects should be deleted.
309 mutable
310 ptr_container_t ptrs;
311
312
313};
314
315
316
317
318}
319
320#endif /* Cloner_H_ */
321
322// Drain
Definition DataSelector.cpp:1277
Definition Cloner.h:46
virtual T & getSource()=0
Returns a reference to an instance.
size_t index_t
Each cloned entry has an index.
Definition Cloner.h:52
virtual const T & getSource() const =0
Returns a reference to an instance (possibly a static one?).
virtual bool drop(index_t i) const =0
Remove cloned entry (experimental)
virtual T & getCloned(index_t i) const =0
Returns an instance at index i.
Wrapper for derived class S, returning base class T.
Definition Cloner.h:118
index_t getNewIndex() const
Remove cloned entries.
Definition Cloner.h:296
S src
Default instance, also the source for cloning.
Definition Cloner.h:275
Cloner(const S &s)
Constructor with source object (copied)
Definition Cloner.h:138
virtual B & getSource()
Returns a reference to a default instance.
Definition Cloner.h:220
virtual const B & getSource() const
Returns a const reference to a default instance.
Definition Cloner.h:211
Cloner(const Cloner< B, S > &c)
Copy constructor.
Definition Cloner.h:134
B & getCloned() const
Implements interface.
Definition Cloner.h:150
virtual S & getSourceOrig()
Returns a reference to a default instance, in actual class.
Definition Cloner.h:238
virtual const S & getSourceOrig() const
Returns a const reference to a default instance, in actual class.
Definition Cloner.h:229
virtual B & getCloned(index_t i) const
Returns.
Definition Cloner.h:175
virtual bool drop(index_t i) const override
Remove cloned entry.
Definition Cloner.h:251
S & getClonedSrc() const
Returns a object of class S, initialized with the source.
Definition Cloner.h:187