Point Cloud Library (PCL)  1.6.0
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
random_sample.hpp
Go to the documentation of this file.
1 /*
2  * Software License Agreement (BSD License)
3  *
4  * Copyright (c) 2009, Willow Garage, Inc.
5  * All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  *
11  * * Redistributions of source code must retain the above copyright
12  * notice, this list of conditions and the following disclaimer.
13  * * Redistributions in binary form must reproduce the above
14  * copyright notice, this list of conditions and the following
15  * disclaimer in the documentation and/or other materials provided
16  * with the distribution.
17  * * Neither the name of Willow Garage, Inc. nor the names of its
18  * contributors may be used to endorse or promote products derived
19  * from this software without specific prior written permission.
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
22  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
23  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
24  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
25  * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
26  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
27  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
28  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
29  * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
30  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
31  * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
32  * POSSIBILITY OF SUCH DAMAGE.
33  *
34  * $Id: random_sample.hpp 5026 2012-03-12 02:51:44Z rusu $
35  *
36  */
37 
38 #ifndef PCL_FILTERS_IMPL_RANDOM_SAMPLE_H_
39 #define PCL_FILTERS_IMPL_RANDOM_SAMPLE_H_
40 
42 
43 
45 template<typename PointT> void
47 {
48  unsigned N = static_cast<unsigned> (input_->size ());
49  float one_over_N = 1.0f / float (N);
50 
51  // If sample size is 0 or if the sample size is greater then input cloud size
52  // then return entire copy of cloud
53  if (sample_ >= N)
54  {
55  output = *input_;
56  }
57  else
58  {
59  // Resize output cloud to sample size
60  output.points.resize (sample_);
61  output.width = sample_;
62  output.height = 1;
63 
64  // Set random seed so derived indices are the same each time the filter runs
65  std::srand (seed_);
66 
67  unsigned top = N - sample_;
68  unsigned i = 0;
69  unsigned index = 0;
70 
71  // Algorithm A
72  for (size_t n = sample_; n >= 2; n--)
73  {
74  unsigned int V = unifRand ();
75  unsigned S = 0;
76  float quot = float (top) * one_over_N;
77  while (quot > V)
78  {
79  S++;
80  top--;
81  N--;
82  quot = quot * float (top) * one_over_N;
83  }
84  index += S;
85  output.points[i++] = input_->points[index++];
86  N--;
87  }
88 
89  index += N * static_cast<unsigned> (unifRand ());
90  output.points[i++] = input_->points[index++];
91  }
92 }
93 
95 template<typename PointT>
96 void
97 pcl::RandomSample<PointT>::applyFilter (std::vector<int> &indices)
98 {
99  unsigned N = static_cast<unsigned> (input_->size ());
100  float one_over_N = 1.0f / float (N);
101 
102  // If sample size is 0 or if the sample size is greater then input cloud size
103  // then return all indices
104  if (sample_ >= N)
105  {
106  indices = *indices_;
107  }
108  else
109  {
110  // Resize output indices to sample size
111  indices.resize (sample_);
112 
113  // Set random seed so derived indices are the same each time the filter runs
114  std::srand (seed_);
115 
116  // Algorithm A
117  unsigned top = N - sample_;
118  unsigned i = 0;
119  unsigned index = 0;
120 
121  for (size_t n = sample_; n >= 2; n--)
122  {
123  unsigned int V = unifRand ();
124  unsigned S = 0;
125  float quot = float (top) * one_over_N;
126  while (quot > V)
127  {
128  S++;
129  top--;
130  N--;
131  quot = quot * float (top) * one_over_N;
132  }
133  index += S;
134  indices[i++] = (*indices_)[index++];
135  N--;
136  }
137 
138  index += N * static_cast<unsigned> (unifRand ());
139  indices[i++] = (*indices_)[index++];
140  }
141 }
142 
143 #define PCL_INSTANTIATE_RandomSample(T) template class PCL_EXPORTS pcl::RandomSample<T>;
144 
145 #endif // PCL_FILTERS_IMPL_RANDOM_SAMPLE_H_