SLAMflex SE  0.1.0
SLAMflex provides detection and tracking of dominant planes for smartphone devices. This plane can then be used to show AR content relative to the plane orientation. The detection of plane is performed in the field of view of the smartphone camera. In subsequent frames it is tracked. The interface returns the plane position and orientation.
allocator.hh
Go to the documentation of this file.
1 // -*- c++ -*-
2 
3 // Copyright (C) 2009 Tom Drummond (twd20@cam.ac.uk),
4 // Ed Rosten (er258@cam.ac.uk)
5 //
6 // This file is part of the TooN Library. This library is free
7 // software; you can redistribute it and/or modify it under the
8 // terms of the GNU General Public License as published by the
9 // Free Software Foundation; either version 2, or (at your option)
10 // any later version.
11 
12 // This library is distributed in the hope that it will be useful,
13 // but WITHOUT ANY WARRANTY; without even the implied warranty of
14 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 // GNU General Public License for more details.
16 
17 // You should have received a copy of the GNU General Public License along
18 // with this library; see the file COPYING. If not, write to the Free
19 // Software Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307,
20 // USA.
21 
22 // As a special exception, you may use this file as part of a free software
23 // library without restriction. Specifically, if other files instantiate
24 // templates or use macros or inline functions from this file, or you compile
25 // this file and link it with other files to produce an executable, this
26 // file does not by itself cause the resulting executable to be covered by
27 // the GNU General Public License. This exception does not however
28 // invalidate any other reasons why the executable file might be covered by
29 // the GNU General Public License.
30 
31 // Allocators always copy data on copy construction.
32 //
33 // When a Vector/Matrix is constructed from a different, but compatible type
34 // copying is done at a much higher level: above the level that knows how the
35 // data is laid out in memory.
36 //
37 // At this level, copy construction is required since it is only known here
38 // whether data or a reference to data should be copied.
39 
40 #ifdef __GNUC__
41 #define TOON_ALIGN8 __attribute__ ((aligned(8)))
42 #else
43 #define TOON_ALIGN8
44 #endif
45 
46 #include "debug.hh"
47 
48 namespace TooN {
49 
50 namespace Internal
51 {
52 
53 template<class Precision> struct DefaultTypes
54 {
55  typedef Precision* PointerType;
56  typedef const Precision* ConstPointerType;
57  typedef Precision& ReferenceType;
58  typedef const Precision& ConstReferenceType;
59 };
60 
61 
62 template<int Size, class Precision, bool heap> class StackOrHeap;
63 
64 template<int Size, class Precision> class StackOrHeap<Size,Precision,0>
65 {
66 public:
68  {
69  debug_initialize(my_data, Size);
70  }
71  Precision my_data[Size];
72 };
73 
74 template<int Size> class StackOrHeap<Size,double,0>
75 {
76 public:
78  {
79  debug_initialize(my_data, Size);
80  }
81  double my_data[Size] TOON_ALIGN8 ;
82 };
83 
84 
85 template<int Size, class Precision> class StackOrHeap<Size, Precision, 1>
86 {
87  public:
89  :my_data(new Precision[Size])
90  {
91  debug_initialize(my_data, Size);
92  }
93 
94 
96  {
97  delete[] my_data;
98  }
99 
100  Precision *my_data;
101 
103  :my_data(new Precision[Size])
104  {
105  for(int i=0; i < Size; i++)
106  my_data[i] = from.my_data[i];
107  }
108 };
109 
116 template<int Size, class Precision> class StaticSizedAllocator: public StackOrHeap<Size, Precision, (sizeof(Precision)*Size>max_bytes_on_stack) >
117 {
118 };
119 
120 
126 template<int Size, class Precision> struct VectorAlloc : public StaticSizedAllocator<Size, Precision>, DefaultTypes<Precision> {
127 
130 
132  VectorAlloc(int /*s*/) { }
133 
135  template<class Op>
137 
139  int size() const {
140  return Size;
141  }
142 
144 
145  Precision *get_data_ptr()
146  {
147  return my_data;
148  };
149 
150  const Precision *get_data_ptr() const
151  {
152  return my_data;
153  }
154 
155  protected:
156 
157  Precision *data()
158  {
159  return my_data;
160  };
161 
162  const Precision *data() const
163  {
164  return my_data;
165  };
166 
168  {}
169 
170  template<class Op> void try_destructive_resize(const Operator<Op>&)
171  {}
172 };
173 
178 template<class Precision> struct VectorAlloc<Dynamic, Precision>: public DefaultTypes<Precision> {
179  Precision * const my_data;
180  const int my_size;
181 
183  :my_data(new Precision[v.my_size]), my_size(v.my_size)
184  {
185  for(int i=0; i < my_size; i++)
186  my_data[i] = v.my_data[i];
187  }
188 
189  VectorAlloc(int s)
190  :my_data(new Precision[s]), my_size(s)
191  {
192  debug_initialize(my_data, my_size);
193  }
194 
195  template <class Op>
197  : my_data(new Precision[op.size()]), my_size(op.size())
198  {
199  debug_initialize(my_data, my_size);
200  }
201 
202  int size() const {
203  return my_size;
204  }
205 
207  delete[] my_data;
208  }
209 
210  Precision *get_data_ptr()
211  {
212  return my_data;
213  };
214 
215  const Precision *get_data_ptr() const
216  {
217  return my_data;
218  }
219 
220  protected:
221 
222  Precision *data()
223  {
224  return my_data;
225  };
226 
227  const Precision *data() const
228  {
229  return my_data;
230  };
231 
233  {}
234 
235  template<class Op> void try_destructive_resize(const Operator<Op>&)
236  {}
237 };
238 
239 
245 template<class Precision> struct VectorAlloc<Resizable, Precision>: public DefaultTypes<Precision> {
246  protected:
247  std::vector<Precision> numbers;
248 
249  public:
250 
252  {
253  }
254 
255  VectorAlloc(int s)
256  :numbers(s)
257  {
258  debug_initialize(data(), size());
259  }
260 
261  template <class Op>
263  :numbers(op.size())
264  {
265  debug_initialize(data(), size());
266  }
267 
268  int size() const {
269  return numbers.size();
270  }
271 
272  Precision *get_data_ptr()
273  {
274  return data();
275  };
276 
277  const Precision *get_data_ptr() const
278  {
279  return data();
280  }
281 
282  protected:
283 
284  Precision* data() {
285  return &numbers[0];
286  }
287 
288  const Precision* data()const {
289  return &numbers[0];
290  }
291 
292  private:
293  //Dymmy class for implementing sfinae
294  //in order to test for a .size() member
295  template<int S> struct SFINAE_dummy{typedef void type;};
296 
297  protected:
298 
299  //SFINAE implementation of try_destructive_resize
300  //to avoid calling .size if it does not exist!
301 
302  //Force the function TYPE to depend on a property
303  //of the Operator<Op> type, so that it simply does
304  //not exist if the property is missing.
305  //Therefore this method only uses .size() if it exists.
306  template<class Op>
307  typename SFINAE_dummy<sizeof(&Operator<Op>::size)>::type try_destructive_resize(const Operator<Op>& op)
308  {
309  try_destructive_resize(op.size());
310  }
311 
312  //Catch-all do nothing for operators with no size method.
313  template<class Op>
314  void try_destructive_resize(const Op&)
315  {}
316 
317  void try_destructive_resize(int newsize)
318  {
319  numbers.resize(newsize);
320  debug_initialize(data(), newsize);
321  }
322 
323  public:
324 
325  void resize(int s)
326  {
327  int old_size = size();
328  numbers.resize(s);
329  if(s > old_size)
330  debug_initialize(data()+old_size, s-old_size);
331  }
332 };
333 
338 //template<int S, class Precision, class PtrType=Precision*, class ConstPtrType=const Precision*, class RefType=Precision&, class ConstRefType=const Precision&> struct VectorSlice
339 template<int S, class Precision, class PtrType=Precision*, class ConstPtrType=const Precision*, class RefType=Precision&, class ConstRefType=const Precision&> struct VectorSlice
340 {
341  int size() const {
342  return S;
343  }
344 
345  //Optional Constructors
346 
347  const PtrType my_data;
348  VectorSlice(PtrType p)
349  :my_data(p){}
350 
351  VectorSlice(PtrType p, int /*size*/)
352  :my_data(p){}
353 
354  template<class Op>
355  VectorSlice(const Operator<Op>& op) : my_data(op.data()) {}
356 
357  protected:
358  PtrType data()
359  {
360  return my_data;
361  };
362 
363  ConstPtrType data() const
364  {
365  return my_data;
366  };
367 
369  {}
370 
371  template<class Op> void try_destructive_resize(const Operator<Op>&)
372  {}
373 
374  public:
375  typedef PtrType PointerType;
376  typedef ConstPtrType ConstPointerType;
377  typedef RefType ReferenceType;
378  typedef ConstRefType ConstReferenceType;
379 };
380 
385 template<class Precision, class PtrType, class ConstPtrType, class RefType, class ConstRefType> struct VectorSlice<Dynamic, Precision, PtrType, ConstPtrType, RefType, ConstRefType>
386 {
387  const PtrType my_data;
388  const int my_size;
389 
390  VectorSlice(PtrType d, int s)
391  :my_data(d), my_size(s)
392  { }
393 
394  template<class Op>
395  VectorSlice(const Operator<Op>& op) : my_data(op.data()), my_size(op.size()) {}
396 
397  int size() const {
398  return my_size;
399  }
400 
401  protected:
402 
403  PtrType data()
404  {
405  return my_data;
406  };
407 
408  ConstPtrType data() const
409  {
410  return my_data;
411  };
412 
414  {}
415 
416  template<class Op> void try_destructive_resize(const Operator<Op>&)
417  {}
418 
419  public:
420  typedef PtrType PointerType;
421  typedef ConstPtrType ConstPointerType;
422  typedef RefType ReferenceType;
423  typedef ConstRefType ConstReferenceType;
424 };
425 
427 //
428 // A class similar to StrideHolder, but to hold the size information for matrices.
429 
436 template<int s> struct SizeHolder
437 {
438  //Constructors ignore superfluous arguments
440  SizeHolder(int){}
441 
443  int size() const{
444  return s;
445  }
446 };
447 
451 template<> struct SizeHolder<-1>
452 {
455  SizeHolder(int s)
456  :my_size(s){}
458 
459  const int my_size;
460  int size() const {
462  return my_size;
463  }
464 };
465 
470 template<int S> struct RowSizeHolder: private SizeHolder<S>
471 {
476  :SizeHolder<S>(i){}
477 
479  {}
480 
484  template<typename Op>
486 
488  int num_rows() const {return SizeHolder<S>::size();}
489 };
490 
491 
496 template<int S> struct ColSizeHolder: private SizeHolder<S>
497 {
502  :SizeHolder<S>(i){}
503 
505  {}
506 
510  template<typename Op>
512 
514  int num_cols() const {return SizeHolder<S>::size();}
515 };
516 
517 
518 
519 template<int R, int C, class Precision, bool FullyStatic=(R>=0 && C>=0)>
521 {
522  MatrixAlloc(int,int)
523  {}
524 
526  {}
527 
528  template <class Op>
530  {}
531 
532  int num_rows() const {
533  return R;
534  }
535 
536  int num_cols() const {
537  return C;
538  }
539 
541 
542  Precision* get_data_ptr()
543  {
544  return my_data;
545  }
546 
547  const Precision* get_data_ptr() const
548  {
549  return my_data;
550  }
551 };
552 
553 
554 template<int R, int C, class Precision> struct MatrixAlloc<R, C, Precision, false>
555  : public RowSizeHolder<R>,
556  ColSizeHolder<C>
557 {
558  Precision* const my_data;
559 
562 
563  // copy constructor so guaranteed contiguous
565  :RowSizeHolder<R>(m.num_rows()),
566  ColSizeHolder<C>(m.num_cols()),
567  my_data(new Precision[num_rows()*num_cols()]) {
568  const int size=num_rows()*num_cols();
569  for(int i=0; i < size; i++) {
570  my_data[i] = m.my_data[i];
571  }
572  }
573 
574  MatrixAlloc(int r, int c)
575  :RowSizeHolder<R>(r),
576  ColSizeHolder<C>(c),
577  my_data(new Precision[num_rows()*num_cols()])
578  {
579  debug_initialize(my_data, num_rows()*num_cols());
580  }
581 
582  template <class Op> MatrixAlloc(const Operator<Op>& op)
583  :RowSizeHolder<R>(op),
584  ColSizeHolder<C>(op),
585  my_data(new Precision[num_rows()*num_cols()])
586  {
587  debug_initialize(my_data, num_rows()*num_cols());
588  }
589 
591  delete[] my_data;
592  }
593 
594  Precision* get_data_ptr()
595  {
596  return my_data;
597  }
598 
599  const Precision* get_data_ptr() const
600  {
601  return my_data;
602  }
603 };
604 
605 
606 template<int R, int C, class Precision> struct MatrixSlice
607  : public RowSizeHolder<R>,
608  ColSizeHolder<C>
609 {
610  Precision* const my_data;
611 
614 
615  //Optional Constructors
616  MatrixSlice(Precision* p)
617  :my_data(p){}
618 
619  MatrixSlice(Precision* p, int r, int c)
620  :RowSizeHolder<R>(r),
621  ColSizeHolder<C>(c),
622  my_data(p){}
623 
624  template<class Op>
626  :RowSizeHolder<R>(op),
627  ColSizeHolder<C>(op),
628  my_data(op.data())
629  {}
630 };
631 
632 
634 //
635 // A class similar to mem, but to hold the stride information. It is only needed
636 // for -1. For +int and -2, the stride is part fo teh type, or implicit.
637 
638 template<int s> struct StrideHolder
639 {
640  //Constructos ignore superfluous arguments
643 
644  template<class Op>
646 
647  int stride() const{
648  return s;
649  }
650 };
651 
652 template<> struct StrideHolder<-1>
653 {
655  :my_stride(s){}
656 
657  template<class Op>
658  StrideHolder(const Operator<Op>& op) : my_stride(op.stride()) {}
659 
660  const int my_stride;
661  int stride() const {
662  return my_stride;
663  }
664 };
665 
666 
667 template<int S> struct RowStrideHolder: public StrideHolder<S>
668 {
670  :StrideHolder<S>(i){}
671 
673  {}
674 
675  template<class Op>
677  : StrideHolder<S>(op)
678  {}
679 
680 };
681 
682 
683 template<int S> struct ColStrideHolder: public StrideHolder<S>
684 {
686  :StrideHolder<S>(i){}
687 
689  {}
690 
691  template<class Op>
693  : StrideHolder<S>(op)
694  {}
695 };
696 
697 }
698 
699 }
700 
701 
702 #undef TOON_ALIGN8
VectorAlloc(const Operator< Op > &)
Construction from an Operator. See Operator::size().
Definition: allocator.hh:136
int size() const
Return the size of the vector.
Definition: allocator.hh:139
const Precision * get_data_ptr() const
Definition: allocator.hh:150
SizeHolder(int)
Construct from an int and discard it.
Definition: allocator.hh:440
int size() const
Simply return the statcally known size.
Definition: allocator.hh:443
VectorAlloc()
Default constructor (only for statically sized vectors)
Definition: allocator.hh:129
const Precision * get_data_ptr() const
Definition: allocator.hh:547
const Precision * ConstPointerType
Definition: allocator.hh:56
VectorSlice(const Operator< Op > &op)
Definition: allocator.hh:355
MatrixAlloc(const Operator< Op > &)
Definition: allocator.hh:529
ColSizeHolder(const Operator< Op > &op)
Definition: allocator.hh:511
Everything lives inside this namespace.
Definition: allocator.hh:48
SFINAE_dummy< sizeof(&Operator< Op >::size)>::type try_destructive_resize(const Operator< Op > &op)
Definition: allocator.hh:307
static const int Dynamic
Template size value used to indicate dynamically sized vectors and matrices.
Definition: TooN.h:272
ColStrideHolder(const Operator< Op > &op)
Definition: allocator.hh:692
static void debug_initialize(P *, int)
Definition: debug.hh:103
StrideHolder(const Operator< Op > &op)
Definition: allocator.hh:658
void try_destructive_resize(const Operator< Op > &)
Definition: allocator.hh:170
MatrixSlice(Precision *p, int r, int c)
Definition: allocator.hh:619
Precision * get_data_ptr()
Definition: allocator.hh:145
Precision * get_data_ptr()
Definition: allocator.hh:542
ConstPtrType data() const
Definition: allocator.hh:363
void try_destructive_resize(const Operator< Op > &)
Definition: allocator.hh:235
void try_destructive_resize(const Operator< Op > &)
Definition: allocator.hh:371
MatrixSlice(const Operator< Op > &op)
Definition: allocator.hh:625
VectorSlice(PtrType p, int)
Definition: allocator.hh:351
Precision *const my_data
Definition: allocator.hh:610
ConstPtrType ConstPointerType
Definition: allocator.hh:376
const Precision * data() const
Definition: allocator.hh:162
SizeHolder()
Default constrution.
Definition: allocator.hh:439
VectorAlloc(int)
Construction from a size (required by damic vectors, ignored otherwise).
Definition: allocator.hh:132
static const int Resizable
Definition: TooN.h:273
const Precision & ConstReferenceType
Definition: allocator.hh:58
RowSizeHolder(const Operator< Op > &op)
Definition: allocator.hh:485
StrideHolder(const Operator< Op > &)
Definition: allocator.hh:645
int num_rows() const
Return the number of rows.
Definition: allocator.hh:488
int num_cols() const
Return the number of columns.
Definition: allocator.hh:514
RowStrideHolder(const Operator< Op > &op)
Definition: allocator.hh:676
ConstRefType ConstReferenceType
Definition: allocator.hh:378