Point Cloud Library (PCL)  1.6.0
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
octree_iterator.h
Go to the documentation of this file.
1 /*
2  * Software License Agreement (BSD License)
3  *
4  * Point Cloud Library (PCL) - www.pointclouds.org
5  * Copyright (c) 2010-2012, Willow Garage, Inc.
6  *
7  * All rights reserved.
8  *
9  * Redistribution and use in source and binary forms, with or without
10  * modification, are permitted provided that the following conditions
11  * are met:
12  *
13  * * Redistributions of source code must retain the above copyright
14  * notice, this list of conditions and the following disclaimer.
15  * * Redistributions in binary form must reproduce the above
16  * copyright notice, this list of conditions and the following
17  * disclaimer in the documentation and/or other materials provided
18  * with the distribution.
19  * * Neither the name of Willow Garage, Inc. nor the names of its
20  * contributors may be used to endorse or promote products derived
21  * from this software without specific prior written permission.
22  *
23  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
24  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
25  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
26  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
27  * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
28  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
29  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
30  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
31  * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
32  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
33  * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
34  * POSSIBILITY OF SUCH DAMAGE.
35  *
36  * $Id: octree_iterator.h 6119 2012-07-03 18:50:04Z aichim $
37  */
38 
39 #ifndef OCTREE_ITERATOR_H
40 #define OCTREE_ITERATOR_H
41 
42 #include <cstddef>
43 #include <vector>
44 #include <deque>
45 
46 #include "octree_nodes.h"
47 #include "octree_key.h"
48 
49 #include <pcl/point_cloud.h>
50 #include <pcl/point_types.h>
51 
52 #include <iterator>
53 
54 // Ignore warnings in the above headers
55 #ifdef __GNUC__
56 #pragma GCC system_header
57 #endif
58 
59 namespace pcl
60 {
61  namespace octree
62  {
68  template<typename DataT, typename OctreeT>
69  class OctreeIteratorBase : public std::iterator<std::forward_iterator_tag, const OctreeNode, void,
70  const OctreeNode*, const OctreeNode&>
71  {
72  public:
73 
74  typedef typename OctreeT::LeafNode LeafNode;
75  typedef typename OctreeT::BranchNode BranchNode;
76 
80  explicit
81  OctreeIteratorBase (OctreeT& octree_arg) :
82  octree_ (octree_arg), currentNode_ (NULL)
83  {
84  reset ();
85  }
86 
91  octree_ (src.octree_), currentNode_ (src.currentNode_), currentOctreeDepth_ (src.currentOctreeDepth_), currentOctreeKey_ (
92  src.currentOctreeKey_)
93  {
94  }
95 
99  inline OctreeIteratorBase&
101  {
102  octree_ = src.octree_;
103  currentNode_ = src.currentNode_;
104  currentOctreeDepth_ = src.currentOctreeDepth_;
105  currentOctreeKey_ = src.currentOctreeKey_;
106  return (*this);
107  }
108 
110  virtual
112  {
113  }
114 
116  inline void
117  reset ()
118  {
119  // initialize iterator globals
120  currentNode_ = static_cast<OctreeNode*> (octree_.getRootNode ());
121  currentOctreeDepth_ = 0;
122 
123  // reset octree key
124  currentOctreeKey_.x = currentOctreeKey_.y = currentOctreeKey_.z = 0;
125  }
126 
130  inline const OctreeKey&
132  {
133  return (currentOctreeKey_);
134  }
135 
139  inline unsigned int
141  {
142  return (currentOctreeDepth_);
143  }
144 
148  inline OctreeNode*
150  {
151  return (currentNode_);
152  }
153 
157  inline OctreeNode*
158  operator* () const
159  { // return designated object
160  return (this->getCurrentOctreeNode ());
161  }
162 
166  inline bool
167  isBranchNode () const
168  {
169  return (currentNode_->getNodeType () == BRANCH_NODE);
170  }
171 
175  inline bool
176  isLeafNode () const
177  {
178  return (currentNode_->getNodeType () == LEAF_NODE);
179  }
180 
184  inline char
186  {
187  char ret = 0;
188 
189  if (isBranchNode ())
190  {
191 
192  // current node is a branch node
193  const BranchNode* currentBranch = static_cast<const BranchNode*> (this->currentNode_);
194 
195  // get child configuration bit pattern
196  ret = octree_.getBranchBitPattern (*currentBranch);
197 
198  }
199 
200  return (ret);
201  }
202 
206  virtual void
207  getData (DataT& data_arg) const
208  {
209 
210  assert(this->currentNode_ );
211 
212  octree_.getDataFromOctreeNode(this->currentNode_, data_arg);
213  }
214 
218  virtual void
219  getData (std::vector<DataT>& dataVector_arg) const
220  {
221  assert(this->currentNode_);
222 
223  octree_.getDataFromOctreeNode(this->currentNode_, dataVector_arg);
224  }
225 
228  virtual std::size_t
229  getSize () const
230  {
231  assert(this->currentNode_);
232 
233  return octree_.getDataSizeFromOctreeNode(this->currentNode_);
234  }
235 
239  virtual unsigned long
240  getNodeID () const
241  {
242  unsigned long id = 0;
243 
244  if (this->currentNode_)
245  {
246  // calculate integer id with respect to octree key
247  unsigned int depth = octree_.getTreeDepth ();
248  id = currentOctreeKey_.x << (depth * 2) | currentOctreeKey_.y << (depth * 1)
249  | currentOctreeKey_.z << (depth * 0);
250  }
251 
252  return id;
253  }
254 
255  protected:
257  OctreeT& octree_;
258 
260  OctreeNode* currentNode_;
261 
263  unsigned int currentOctreeDepth_;
264 
266  OctreeKey currentOctreeKey_;
267  };
268 
270 
275  template<typename DataT, typename OctreeT>
276  class OctreeDepthFirstIterator : public OctreeIteratorBase<DataT, OctreeT>
277  {
278 
279  public:
280 
283 
284 
288  explicit
289  OctreeDepthFirstIterator (OctreeT& octree_arg);
290 
292  virtual
294 
295 
298  virtual void
299  reset ();
300 
305  operator++ ();
306 
312  {
313  OctreeDepthFirstIterator _Tmp = *this;
314  ++*this;
315  return (_Tmp);
316  }
317 
320  void
321  skipChildVoxels ();
322 
323  protected:
325  unsigned char currentChildIdx_;
326 
328  std::vector<std::pair<OctreeNode*, unsigned char> > stack_;
329  };
330 
332 
337  template<typename DataT, typename OctreeT>
338  class OctreeBreadthFirstIterator : public OctreeIteratorBase<DataT, OctreeT>
339  {
340  // public typedefs
343 
344  struct FIFOElement
345  {
346  OctreeNode* node;
347  OctreeKey key;
348  unsigned int depth;
349  };
350 
351  public:
355  explicit
356  OctreeBreadthFirstIterator (OctreeT& octree_arg);
357 
359  virtual
361 
364  void
365  reset ();
366 
371  operator++ ();
372 
378  {
379  OctreeBreadthFirstIterator _Tmp = *this;
380  ++*this;
381  return (_Tmp);
382  }
383 
384  protected:
388  void
389  addChildNodesToFIFO (const OctreeNode* node);
390 
392  std::deque<FIFOElement> FIFO_;
393  };
394 
396 
401 
402  template<typename DataT, typename OctreeT>
403  class OctreeLeafNodeIterator : public OctreeDepthFirstIterator<DataT, OctreeT>
404  {
407 
408  public:
412  explicit
413  OctreeLeafNodeIterator (OctreeT& octree_arg) :
414  OctreeDepthFirstIterator<DataT, OctreeT> (octree_arg)
415  {
416  reset ();
417  }
418 
420  virtual
422  {
423  }
424 
427  inline void
428  reset ()
429  {
431  }
432 
436  inline OctreeLeafNodeIterator&
438  {
439  do
440  {
442  } while ((this->currentNode_) && (this->currentNode_->getNodeType () != LEAF_NODE));
443 
444  return (*this);
445  }
446 
452  {
453  OctreeLeafNodeIterator _Tmp = *this;
454  ++*this;
455  return (_Tmp);
456  }
457 
461  OctreeNode*
462  operator* () const
463  {
464  // return designated object
465  OctreeNode* ret = 0;
466 
467  if (this->currentNode_ && (this->currentNode_->getNodeType () == LEAF_NODE))
468  ret = this->currentNode_;
469  return (ret);
470  }
471  };
472 
473  }
474 }
475 
476 #endif
477