Point Cloud Library (PCL) 1.12.0
Loading...
Searching...
No Matches
multi_channel_2d_comparison_feature_handler.h
1/*
2 * Software License Agreement (BSD License)
3 *
4 * Point Cloud Library (PCL) - www.pointclouds.org
5 * Copyright (c) 2010-2011, 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 */
37
38#pragma once
39
40#include <pcl/common/common.h>
41#include <pcl/ml/feature_handler.h>
42#include <pcl/ml/multi_channel_2d_comparison_feature.h>
43#include <pcl/ml/multi_channel_2d_data_set.h>
44#include <pcl/ml/multiple_data_2d_example_index.h>
45#include <pcl/ml/point_xy_32f.h>
46#include <pcl/ml/point_xy_32i.h>
47
48#include <istream>
49#include <ostream>
50
51namespace pcl {
52
53/** Feature utility class that handles the creation and evaluation of RGBD
54 * comparison features. */
55template <class DATA_TYPE, std::size_t NUM_OF_CHANNELS>
57: public pcl::FeatureHandler<pcl::MultiChannel2DComparisonFeature<pcl::PointXY32i>,
58 pcl::MultiChannel2DDataSet<DATA_TYPE, NUM_OF_CHANNELS>,
59 pcl::MultipleData2DExampleIndex> {
60
61public:
62 /** Constructor. */
64 const int feature_window_height)
65 : feature_window_width_(feature_window_width)
66 , feature_window_height_(feature_window_height)
67 {}
68
69 /** Destructor. */
71
72 /** Sets the feature window size.
73 *
74 * \param[in] width the width of the feature window
75 * \param[in] height the height of the feature window
76 */
77 inline void
78 setFeatureWindowSize(int width, int height)
79 {
80 feature_window_width_ = width;
81 feature_window_height_ = height;
82 }
83
84 /** Creates random features.
85 *
86 * \param[in] num_of_features the number of random features to create
87 * \param[out] features the destination for the created random features
88 */
89 inline void
91 const std::size_t num_of_features,
93 {
94 features.resize(num_of_features);
95 for (std::size_t feature_index = 0; feature_index < num_of_features;
96 ++feature_index) {
97 features[feature_index].p1 = PointXY32i::randomPoint(-feature_window_width_ / 2,
98 feature_window_width_ / 2,
99 -feature_window_height_ / 2,
100 feature_window_height_ / 2);
101 features[feature_index].p2 = PointXY32i::randomPoint(-feature_window_width_ / 2,
102 feature_window_width_ / 2,
103 -feature_window_height_ / 2,
104 feature_window_height_ / 2);
105 features[feature_index].channel = static_cast<unsigned char>(
106 NUM_OF_CHANNELS * (static_cast<float>(rand()) / (RAND_MAX + 1)));
107 }
108 }
109
110 /** Evaluates a feature for a set of examples on the specified data set.
111 *
112 * \param[in] feature the feature to evaluate
113 * \param[in] data_set the data set the feature is evaluated on
114 * \param[in] examples the examples the feature is evaluated for
115 * \param[out] results the destination for the evaluation results
116 * \param[out] flags the destination for the flags corresponding to the evaluation
117 * results
118 */
119 inline void
122 std::vector<MultipleData2DExampleIndex>& examples,
123 std::vector<float>& results,
124 std::vector<unsigned char>& flags) const
125 {
126 results.resize(examples.size());
127 flags.resize(examples.size());
130
131 evaluateFeature(
133 }
134 }
135
136 /** Evaluates a feature for one examples on the specified data set.
137 *
138 * \param[in] feature the feature to evaluate
139 * \param[in] data_set the data set the feature is evaluated on
140 * \param[in] example the example the feature is evaluated for
141 * \param[out] result the destination for the evaluation result
142 * \param[out] flag the destination for the flag corresponding to the evaluation
143 * result
144 */
145 inline void
149 float& result,
150 unsigned char& flag) const
151 {
152 const int center_col_index = example.x;
153 const int center_row_index = example.y;
154
155 const std::size_t p1_col =
156 static_cast<std::size_t>(feature.p1.x + center_col_index);
157 const std::size_t p1_row =
158 static_cast<std::size_t>(feature.p1.y + center_row_index);
159
160 const std::size_t p2_col =
161 static_cast<std::size_t>(feature.p2.x + center_col_index);
162 const std::size_t p2_row =
163 static_cast<std::size_t>(feature.p2.y + center_row_index);
164
165 const unsigned char channel = feature.channel;
166
167 const float value1 =
168 static_cast<float>(data_set(example.data_set_id, p1_col, p1_row)[channel]);
169 const float value2 =
170 static_cast<float>(data_set(example.data_set_id, p2_col, p2_row)[channel]);
171
172 result = value1 - value2;
173 flag = (std::isfinite(value1) && std::isfinite(value2)) ? 0 : 1;
174 }
175
176 /** Generates code for feature evaluation.
177 *
178 * \param[in] feature the feature for which code is generated
179 * \param[out] stream the destination for the generated code
180 */
181 void
183 std::ostream& stream) const
184 {
185 stream << "ERROR: RegressionVarianceStatsEstimator does not implement "
186 "generateCodeForBranchIndex(...)";
187 // stream << "const float value = ( (*dataSet)(dataSetId, centerY+" << feature.p1.y
188 // << ", centerX+" << feature.p1.x << ")[" << static_cast<int>(feature.colorChannel)
189 // << "]"
190 // << " - " << "(*dataSet)(dataSetId, centerY+" << feature.p2.y << ", centerX+" <<
191 // feature.p2.x << ")[" << static_cast<int>(feature.colorChannel) << "] );" <<
192 // ::std::endl;
193 }
194
195private:
196 /** The width of the feature window. */
197 int feature_window_width_;
198 /** The height of the feature window. */
199 int feature_window_height_;
200};
201
202/** Feature utility class that handles the creation and evaluation of RGBD
203 * comparison features. */
204template <class DATA_TYPE,
205 std::size_t NUM_OF_CHANNELS,
206 std::size_t SCALE_CHANNEL,
207 bool INVERT_SCALE>
209: public pcl::FeatureHandler<pcl::MultiChannel2DComparisonFeature<pcl::PointXY32f>,
210 pcl::MultiChannel2DDataSet<DATA_TYPE, NUM_OF_CHANNELS>,
211 pcl::MultipleData2DExampleIndex> {
212
213public:
214 /** Constructor. */
216 const int feature_window_height)
217 : feature_window_width_(feature_window_width)
218 , feature_window_height_(feature_window_height)
219 {}
220
221 /** Destructor. */
223
224 /** Sets the feature window size.
225 *
226 * \param[in] width the width of the feature window
227 * \param[in] height the height of the feature window
228 */
229 inline void
230 setFeatureWindowSize(int width, int height)
231 {
232 feature_window_width_ = width;
233 feature_window_height_ = height;
234 }
235
236 /** Creates random features.
237 *
238 * \param[in] num_of_features the number of random features to create
239 * \param[out] features the destination for the created random features
240 */
241 inline void
243 const std::size_t num_of_features,
244 std::vector<MultiChannel2DComparisonFeature<PointXY32f>>& features)
245 {
246 features.resize(num_of_features);
247 for (std::size_t feature_index = 0; feature_index < num_of_features;
248 ++feature_index) {
249 features[feature_index].p1 = PointXY32f::randomPoint(-feature_window_width_ / 2,
250 feature_window_width_ / 2,
251 -feature_window_height_ / 2,
252 feature_window_height_ / 2);
253 features[feature_index].p2 = PointXY32f::randomPoint(-feature_window_width_ / 2,
254 feature_window_width_ / 2,
255 -feature_window_height_ / 2,
256 feature_window_height_ / 2);
257 features[feature_index].channel = static_cast<unsigned char>(
258 NUM_OF_CHANNELS * (static_cast<float>(rand()) / (RAND_MAX + 1)));
259 }
260 }
261
262 /** Evaluates a feature for a set of examples on the specified data set.
263 *
264 * \param[in] feature the feature to evaluate
265 * \param[in] data_set the data set the feature is evaluated on
266 * \param[in] examples the examples the feature is evaluated for
267 * \param[out] results the destination for the evaluation results
268 * \param[out] flags the destination for the flags corresponding to the evaluation
269 * results
270 */
271 inline void
274 std::vector<MultipleData2DExampleIndex>& examples,
275 std::vector<float>& results,
276 std::vector<unsigned char>& flags) const
277 {
278 results.resize(examples.size());
279 flags.resize(examples.size());
282
283 evaluateFeature(
285 }
286 }
287
288 /** Evaluates a feature for one examples on the specified data set.
289 *
290 * \param[in] feature the feature to evaluate
291 * \param[in] data_set the data set the feature is evaluated on
292 * \param[in] example the example the feature is evaluated for
293 * \param[out] result the destination for the evaluation result
294 * \param[out] flag the destination for the flag corresponding to the evaluation
295 * result
296 */
297 inline void
301 float& result,
302 unsigned char& flag) const
303 {
304 const int center_col_index = example.x;
305 const int center_row_index = example.y;
306
307 float scale;
308 if (INVERT_SCALE)
309 scale = 1.0f / static_cast<float>(data_set(example.data_set_id,
312 else
313 scale = static_cast<float>(data_set(
315
316 const std::size_t p1_col =
317 static_cast<std::size_t>(scale * feature.p1.x + center_col_index);
318 const std::size_t p1_row =
319 static_cast<std::size_t>(scale * feature.p1.y + center_row_index);
320
321 const std::size_t p2_col =
322 static_cast<std::size_t>(scale * feature.p2.x + center_col_index);
323 const std::size_t p2_row =
324 static_cast<std::size_t>(scale * feature.p2.y + center_row_index);
325
326 const unsigned char channel = feature.channel;
327
328 const float value1 =
329 static_cast<float>(data_set(example.data_set_id, p1_col, p1_row)[channel]);
330 const float value2 =
331 static_cast<float>(data_set(example.data_set_id, p2_col, p2_row)[channel]);
332
333 result = value1 - value2;
334 flag = (std::isfinite(value1) && std::isfinite(value2)) ? 0 : 1;
335 }
336
337 /** Generates code for feature evaluation.
338 *
339 * \param[in] feature the feature for which code is generated
340 * \param[out] stream the destination for the generated code
341 */
342 void
344 std::ostream& stream) const
345 {
346 stream << "ERROR: ScaledMultiChannel2DComparisonFeatureHandler does not implement "
347 "generateCodeForBranchIndex(...)"
348 << std::endl;
349
350 // pcl::PointXY32f p1 = feature.p1;
351 // pcl::PointXY32f p2 = feature.p2;
352
353 // stream << "const float eval_value = data_ptr + " << p1.x << " + " << p1.y << " *
354 // width;
355
356 // stream << "const float value = ( (*dataSet)(dataSetId, centerY+" << feature.p1.y
357 // << ", centerX+" << feature.p1.x << ")[" << static_cast<int>(feature.colorChannel)
358 // << "]"
359 // << " - " << "(*dataSet)(dataSetId, centerY+" << feature.p2.y << ", centerX+" <<
360 // feature.p2.x << ")[" << static_cast<int>(feature.colorChannel) << "] );" <<
361 // ::std::endl;
362 }
363
364private:
365 /** The width of the feature window. */
366 int feature_window_width_;
367 /** The height of the feature window. */
368 int feature_window_height_;
369};
370
371template <class DATA_TYPE,
372 std::size_t NUM_OF_CHANNELS,
373 std::size_t SCALE_CHANNEL,
374 bool INVERT_SCALE>
376: public pcl::FeatureHandlerCodeGenerator<
377 pcl::MultiChannel2DComparisonFeature<pcl::PointXY32f>,
378 pcl::MultiChannel2DDataSet<DATA_TYPE, NUM_OF_CHANNELS>,
379 pcl::MultipleData2DExampleIndex> {
380public:
383
384 void
385 generateEvalFunctionCode(std::ostream& stream) const;
386
387 void
388 generateEvalCode(const MultiChannel2DComparisonFeature<PointXY32f>& feature,
389 std::ostream& stream) const;
390};
391
392template <class DATA_TYPE,
393 std::size_t NUM_OF_CHANNELS,
394 std::size_t SCALE_CHANNEL,
395 bool INVERT_SCALE>
396void
397ScaledMultiChannel2DComparisonFeatureHandlerCCodeGenerator<
398 DATA_TYPE,
399 NUM_OF_CHANNELS,
400 SCALE_CHANNEL,
401 INVERT_SCALE>::generateEvalFunctionCode(std::ostream& stream) const
402{
403 if (NUM_OF_CHANNELS == 1 && SCALE_CHANNEL == 0 && INVERT_SCALE) {
404 stream << "const float scale = 1.0f / static_cast<float> (*data_ptr);"
405 << std::endl;
406 stream << "" << std::endl;
407 stream << "struct LocalFeatureHandler" << std::endl;
408 stream << "{" << std::endl;
409 stream << " static inline void eval (" << typeid(DATA_TYPE).name()
410 << " * a_ptr, const float a_x1, const float a_y1, const float a_x2, const "
411 "float a_y2, const float a_scale, const int a_width, float & a_result, "
412 "unsigned char & a_flags)"
413 << std::endl;
414 stream << " {" << std::endl;
415 stream << " a_result = *(a_ptr + static_cast<int> (a_scale*a_x1) + "
416 "(static_cast<int> (a_scale*a_y1)*a_width)) - *(a_ptr + static_cast<int> "
417 "(a_scale*a_x2) + (static_cast<int> (a_scale*a_y2)*a_width));"
418 << std::endl;
419 stream << " }" << std::endl;
420 stream << "};" << std::endl;
421 }
422 else {
423 stream << "ERROR: generateEvalFunctionCode not implemented" << std::endl;
424 }
425}
426
427template <class DATA_TYPE,
428 std::size_t NUM_OF_CHANNELS,
429 std::size_t SCALE_CHANNEL,
430 bool INVERT_SCALE>
431void
436 generateEvalCode(const MultiChannel2DComparisonFeature<PointXY32f>& feature,
437 std::ostream& stream) const
438{
439 stream << "LocalFeatureHandler::eval (data_ptr, " << feature.p1.x << ", "
440 << feature.p1.y << ", " << feature.p2.x << ", " << feature.p2.y << ", "
441 << "scale, width, result, flags);" << std::endl;
442}
443
450
457
460
461} // namespace pcl
Iterator class for point clouds with or without given indices.
std::size_t size() const
Size of the range the iterator is going through.
Utility class interface which is used for creating and evaluating features.
Feature utility class that handles the creation and evaluation of RGBD comparison features.
void evaluateFeature(const MultiChannel2DComparisonFeature< PointXY32i > &feature, MultiChannel2DDataSet< DATA_TYPE, NUM_OF_CHANNELS > &data_set, std::vector< MultipleData2DExampleIndex > &examples, std::vector< float > &results, std::vector< unsigned char > &flags) const
Evaluates a feature for a set of examples on the specified data set.
void setFeatureWindowSize(int width, int height)
Sets the feature window size.
void evaluateFeature(const MultiChannel2DComparisonFeature< PointXY32i > &feature, MultiChannel2DDataSet< DATA_TYPE, NUM_OF_CHANNELS > &data_set, const MultipleData2DExampleIndex &example, float &result, unsigned char &flag) const
Evaluates a feature for one examples on the specified data set.
MultiChannel2DComparisonFeatureHandler(const int feature_window_width, const int feature_window_height)
Constructor.
void generateCodeForEvaluation(const MultiChannel2DComparisonFeature< PointXY32i > &feature, std::ostream &stream) const
Generates code for feature evaluation.
void createRandomFeatures(const std::size_t num_of_features, std::vector< MultiChannel2DComparisonFeature< PointXY32i > > &features)
Creates random features.
Feature utility class that handles the creation and evaluation of RGBD comparison features.
void evaluateFeature(const MultiChannel2DComparisonFeature< PointXY32f > &feature, MultiChannel2DDataSet< DATA_TYPE, NUM_OF_CHANNELS > &data_set, std::vector< MultipleData2DExampleIndex > &examples, std::vector< float > &results, std::vector< unsigned char > &flags) const
Evaluates a feature for a set of examples on the specified data set.
void evaluateFeature(const MultiChannel2DComparisonFeature< PointXY32f > &feature, MultiChannel2DDataSet< DATA_TYPE, NUM_OF_CHANNELS > &data_set, const MultipleData2DExampleIndex &example, float &result, unsigned char &flag) const
Evaluates a feature for one examples on the specified data set.
void generateCodeForEvaluation(const MultiChannel2DComparisonFeature< PointXY32f > &feature, std::ostream &stream) const
Generates code for feature evaluation.
void createRandomFeatures(const std::size_t num_of_features, std::vector< MultiChannel2DComparisonFeature< PointXY32f > > &features)
Creates random features.
void setFeatureWindowSize(int width, int height)
Sets the feature window size.
ScaledMultiChannel2DComparisonFeatureHandler(const int feature_window_width, const int feature_window_height)
Constructor.
Define standard C methods and C++ classes that are common to all methods.
Example index for a set of 2D data blocks.