VariableBase.h
1 /*
2 
3 MIT License
4 
5 Copyright (c) 2017 FMI Open Development / Markus Peura, first.last@fmi.fi
6 
7 Permission is hereby granted, free of charge, to any person obtaining a copy
8 of this software and associated documentation files (the "Software"), to deal
9 in the Software without restriction, including without limitation the rights
10 to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
11 copies of the Software, and to permit persons to whom the Software is
12 furnished to do so, subject to the following conditions:
13 
14 The above copyright notice and this permission notice shall be included in all
15 copies or substantial portions of the Software.
16 
17 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
20 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
22 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
23 SOFTWARE.
24 
25 */
26 /*
27 Part of Rack development has been done in the BALTRAD projects part-financed
28 by the European Union (European Regional Development Fund and European
29 Neighbourhood Partnership Instrument, Baltic Sea Region Programme 2007-2013)
30 */
31 
32 
33 
34 #ifndef DRAIN_VARIABLE_BASE
35 #define DRAIN_VARIABLE_BASE
36 
37 #include "Castable.h"
38 #include "CastableIterator.h"
39 
40 #include "VariableT.h"
41 
42 
43 namespace drain {
44 
45 
47 
56 class VariableBase : public Castable {
57 
58 public:
59 
60  // Like in images. Should be fixed.
62  typedef CastableIterator iterator;
63 
64  //typedef std::pair<const char *,const drain::VariableBase> init_pair_t;
65 
66 
67  virtual inline
68  ~VariableBase(){};
69 
71 
74  virtual inline // true also if ptr == null
75  bool isLinking() const {
76  if (caster.ptr == nullptr){
77  return false;
78  }
79  else if (data.empty()){ // this is never true
80  return true;
81  }
82  else {
83  return (caster.ptr != (void *) &data[0]);
84  /*
85  if (caster.ptr != (void *) &data[0]){ // Debugging
86  std::cerr << __FILE__ << ':' << __LINE__ << ':' << __FUNCTION__ << " non-empty data [" << getTypeName() << "], but pointer discarding it " << std::endl;
87  std::cerr << __FILE__ << ':' << __LINE__ << ':' << __FUNCTION__ << " value: '" << *this << "'" << std::endl;
88  //info(std::cerr);
89  }
90  return false;
91  */
92  }
93 
94  }
95 
97 
104  virtual inline
105  bool isVariable() const {
106  return true;
107  }
108 
109 
111 
114  virtual inline
115  bool isLinkable() const {
116  return false;
117  }
118 
119 
120  /* Trying to raise to Castable
121  VariableBase & append(){
122  return *this;
123  }
124 
125  template <class T, class ...TT>
126  VariableBase & append(const T &x, const TT& ...rest){
127  Castable::operator<<(x);
128  append(rest...);
129  return *this;
130  }
131  */
132 
133  template <class T, class ...TT>
134  // VariableBase &
135  void set(const T &arg, const TT& ...args){
136  clear();
137  // (*this) = x; // 2025
138  assign(arg); // 2025
139  //return append(rest...);
140  append(args...);
141  }
142 
144  /*
145  inline
146  void reset(){
147  caster.unsetType();
148  //resize(0);
149  updateSize(0);
150  setSeparator(',');
151  //this->separator = ','; // semantics ?
152  }
153  */
154 
156 
159  virtual
160  void setType(const std::type_info & t);
161 
162 
163 
165  /*
166  * Note: if a std::string is given, does not split it like with Variable::operator=(const char *).
167  */
168  template <class T>
169  inline
170  VariableBase &operator<<(const T &x){
171  //Castable::operator<<(x);
172  append(x);
173  return *this;
174  }
175 
176 
177 
179 
182  inline
183  const CastableIterator & begin() const { return dataBegin; };
184 
186  /*
187  * Notice: in the case of std::strings, will iterate through characters.
188  */
189  inline
190  const CastableIterator & end() const { return dataEnd; };
191 
192 
194 
197  virtual inline
198  bool setSize(size_t elementCount){
199  updateSize(elementCount);
200  return true;
201  }
202 
204  virtual inline
205  void ensureSize(size_t elementCount){
206  if (this->elementCount < elementCount){
207  updateSize(elementCount);
208  }
209  // return true;
210  }
211 
212 protected:
213 
214 
215  /***
216  * This is the basic design pattern for all the VariableLikes
217  template <class ...TT>
218  inline
219  VariableBase(const TT & ...args) {
220  init(args...); //
221  }
222  */
223 
224  virtual
225  void updateSize(size_t elementCount);
226 
227 private:
228 
229  std::vector<char> data;
230 
231  mutable CastableIterator dataBegin;
232  mutable CastableIterator dataEnd;
233 
234 
235 private:
236 
237  void updateIterators();
238 
239 };
240 
241 /*
242 template <class T>
243 class VariableT<T>;
244 */
245 
249 template <class V>
250 class VariableInitializer : public V {
251 
252 protected:
253 
255  /*
256  template <class T>
257  void init(const VariableInitializer<V> & value) {
258  std::cerr << __FILE__ << ':' << __LINE__ << ':' << __FUNCTION__ << " " << value << '[' << typeid(T).name() << ']'<< std::endl;
259  this->reset();
260  this->assignCastable(value);
261  }
262  */
263 
264 
266 
272  template <class T>
273  void init(const VariableT<T> & value) {
274  // drain::Logger(__FILE__, __LINE__, __FUNCTION__).warn(drain::TypeName<VariableT<VariableInitializer<V> > >::str(),
275  // '(', drain::TypeName<VariableT<T> >::str(), ' ', value, ')');
276  this->reset();
277  this->assignCastable(value);
278  }
279 
280  template <class T>
281  void init(VariableT<T> & value) {
282  // drain::Logger(__FILE__, __LINE__, __FUNCTION__).warn(drain::TypeName<VariableT<VariableInitializer<V> > >::str(),
283  // '(', drain::TypeName<VariableT<T> >::str(), ' ', value, ')');
284  this->reset();
285  if (value.isLinking() && this->isLinkable()){
286  this->relink(value);
287  // this->setPtr(value.getPtr(), value.getType(), value.getElementCount());
288  }
289  this->assignCastable(value);
290  }
291 
292 
293  /*
294  template <class D>
295  void init(const D & dst){
296  reset();
297  assign(dst);
298  }
299  */
301  inline
302  void init(const std::type_info &t = typeid(void)) {
303  this->reset();
304  this->setType(t);
305  };
306 
307  // Initialisation, using type of argument or explicit type argument.
308  // Copies type, data and separator char. Fails with Reference?
309  template <class T>
310  void init(const T & value) {
311  // std::cerr << __FILE__ << ':' << __LINE__ << ':' << __FUNCTION__ << " " << value << '[' << typeid(T).name() << ']'<< std::endl;
312  // std::cerr << __LINE__ << " reset: " << std::endl;
313  this->reset();
314  // std::cerr << __LINE__ << " assign: " << std::endl;
315  this->assign(value); // Critical, direct assignment *this = value fails
316  // std::cerr << __LINE__ << " ...done " << std::endl;
317  }
318 
319 
320  template <class T>
321  void init(const T & value, const std::type_info &t) { // = typeid(void)
322  std::cerr << __FILE__ << ':' << __LINE__ << ':' << __FUNCTION__ << " " << value << '[' << t.name() << ']' << std::endl;
323 
324  std::cerr << __LINE__ << " reset: " << std::endl;
325  this->reset();
326  std::cerr << __LINE__ << " setType: " << std::endl;
327  this->setType(t);
328  std::cerr << __LINE__ << " assign: " << std::endl;
329  this->assign(value); // Critical, direct assignment *this = value fails
330  std::cerr << __LINE__ << " ...done " << std::endl;
331  // ;
332  }
333 
334 
336  inline
337  void init(const VariableBase & v) {
338  std::cerr << __FILE__ << ':' << __LINE__ << __FUNCTION__ << " " << v << std::endl;
339  this->reset();
340  this->outputSeparator = v.outputSeparator;
341  this->inputSeparator = v.inputSeparator;
342  this->assignCastable(v);
343  };
344 
346  inline
347  void init(const Castable & c) {
348  std::cerr << __FILE__ << ':' << __LINE__ << __FUNCTION__ << " " << c << std::endl;
349  this->reset();
350  //this->outputSeparator = c.outputSeparator;
351  //this->inputSeparator = c.inputSeparator;
352  this->assignCastable(c);
353  };
354 
356  inline
357  void init(const char * s) {
358  // std::cerr << __FILE__ << ':' << __LINE__ << __FUNCTION__ << " " << s << std::endl;
359  this->reset();
360  this->assignString(s);
361  };
362 
364  template<typename T>
365  inline
366  void init(std::initializer_list<T> l, const std::type_info &t = typeid(void)) {
367  // std::cerr << __FILE__ << ':' << __LINE__ << __FUNCTION__ << " " << std::endl;
368  this->reset();
369  this->setType(t);
370  this->assignContainer(l, true);
371  };
372 
373  template <class ...TT>
374  void init(const TT& ...args){
375  // std::cerr << __FILE__ << ':' << __LINE__ << __FUNCTION__ << " (variadic args)" << std::endl;
376  this->reset();
377  this->append(args...);
378  }
379 
380 };
381 
382 }
383 
384 #endif
Definition: CastableIterator.h:57
Definition: Castable.h:76
size_t elementCount
Pointer to the data variable.
Definition: Castable.h:1233
char outputSeparator
Element separator usein in writing and reading character strings (streams).
Definition: Castable.h:1239
char inputSeparator
Element separator usein in reading a char sequence to an (numeric) array.
Definition: Castable.h:1236
void clear()
Clears strings, or for scalars and arrays, sets all the values to zero. Does not change type.
Definition: Castable.cpp:81
void setType()
Sets the storage type. If a target value is available, use setPtr() directly.
Definition: Castable.h:873
void append(const T &x)
Appends the string or appends the array by one element.
Definition: Castable.h:419
void * ptr
Future member: enables setting Caster type.
Definition: Caster.h:247
Base class for variables: Variable, Reference and FlexibleVariable.
Definition: VariableBase.h:56
virtual bool isLinking() const
Tells if the pointer points to an external variable.
Definition: VariableBase.h:75
const CastableIterator & end() const
Like with std::iterator.
Definition: VariableBase.h:190
virtual bool setSize(size_t elementCount)
Extends the array to include elementCount elements of current type.
Definition: VariableBase.h:198
virtual bool isVariable() const
Tells if internal memory exists.
Definition: VariableBase.h:105
VariableBase & operator<<(const T &x)
Extends the array by one element.
Definition: VariableBase.h:170
virtual bool isLinkable() const
Tells if the internal pointer can point to an external variable.
Definition: VariableBase.h:115
const CastableIterator & begin() const
Like with std::iterator.
Definition: VariableBase.h:183
Definition: VariableBase.h:250
void init(const Castable &c)
Copies type, data and separator char.
Definition: VariableBase.h:347
void init(const char *s)
Copies type, data and separator char.
Definition: VariableBase.h:357
void init(std::initializer_list< T > l, const std::type_info &t=typeid(void))
Initialisation with type of the first element or explicit type argument.
Definition: VariableBase.h:366
void init(const std::type_info &t=typeid(void))
Default constructor generates an empty array.
Definition: VariableBase.h:302
void init(const VariableBase &v)
Copies type, data and separator char.
Definition: VariableBase.h:337
void init(const VariableT< T > &value)
Copy constructor handler.
Definition: VariableBase.h:273
VariableT is a final class applied through typedefs Variable, Reference and FlexibleVariable.
Definition: VariableT.h:87
Definition: DataSelector.cpp:1277