41 #include "Eigen/Eigenvalues"
58 averageExistingDescriptors(
Parametrizable::
get<bool>(
"averageExistingDescriptors")),
77 inPlaceFilter(output);
90 const int pointsCount(cloud.
features.cols());
91 const int featDim(cloud.
features.rows());
96 if (averageExistingDescriptors)
100 for(
unsigned int i = 0; i < labelDim; ++i)
102 if (insertDim != descDim)
103 throw InvalidField(
"ElipsoidsDataPointsFilter: Error, descriptor labels do not match descriptor data");
107 const int dimNormals(featDim-1);
108 const int dimDensities(1);
109 const int dimEigValues(featDim-1);
110 const int dimEigVectors((featDim-1)*(featDim-1));
111 const int dimWeights(1);
112 const int dimMeans(featDim-1);
113 const int dimCovariances((featDim-1)*(featDim-1));
114 const int dimShapes(featDim-1);
115 const int dimPointIds(
knn);
118 Labels cloudLabels, timeLabels;
121 cloudLabels.push_back(
Label(
"pointIds", dimPointIds));
122 cloudLabels.push_back(
Label(
"pointX", dimPointIds));
123 cloudLabels.push_back(
Label(
"pointY", dimPointIds));
124 cloudLabels.push_back(
Label(
"pointZ", dimPointIds));
125 cloudLabels.push_back(
Label(
"numOfNN", 1));
128 cloudLabels.push_back(
Label(
"normals", dimNormals));
130 cloudLabels.push_back(
Label(
"densities", dimDensities));
132 cloudLabels.push_back(
Label(
"eigValues", dimEigValues));
133 if (keepEigenVectors)
134 cloudLabels.push_back(
Label(
"eigVectors", dimEigVectors));
136 cloudLabels.push_back(
Label(
"covariance", dimCovariances));
138 cloudLabels.push_back(
Label(
"weights", dimWeights));
140 cloudLabels.push_back(
Label(
"means", dimMeans));
143 assert(featDim == 3);
144 cloudLabels.push_back(
Label(
"shapes", dimShapes));
146 timeLabels.push_back(
Label(
"time", 2));
153 TimeView cloudExistingTimes(cloud.
times.block(0,0,cloud.
times.rows(),cloud.
times.cols()));
171 if (keepEigenVectors)
187 cloud.
features.rowwise().minCoeff(),
195 for (
int i = 0; i < ptsOut; ++i)
224 buildData.
means->col(i) = buildData.
means->col(k);
228 cloud.
features.conservativeResize(Eigen::NoChange, ptsOut);
229 cloud.
descriptors.conservativeResize(Eigen::NoChange, ptsOut);
230 cloud.
times.conservativeResize(Eigen::NoChange, ptsOut);
244 const int count(last - first);
245 if (count <=
int(
knn))
248 fuseRange(
data, first, last);
254 const int cutDim = argMax<T>(maxValues - minValues);
257 const int rightCount(count/2);
258 const int leftCount(count - rightCount);
259 assert(last - rightCount == first + leftCount);
263 data.indices.begin() + first,
264 data.indices.begin() + first + leftCount,
265 data.indices.begin() + last,
270 const int cutIndex(
data.indices[first+leftCount]);
271 const T cutVal(
data.features(cutDim, cutIndex));
274 Vector leftMaxValues(maxValues);
275 leftMaxValues[cutDim] = cutVal;
277 Vector rightMinValues(minValues);
278 rightMinValues[cutDim] = cutVal;
281 buildNew(
data, first, first + leftCount, std::forward<Vector>(minValues), std::move(leftMaxValues));
282 buildNew(
data, first + leftCount, last, std::move(rightMinValues), std::forward<Vector>(maxValues));
291 typedef typename Eigen::Matrix<std::int64_t, Eigen::Dynamic, Eigen::Dynamic>
Int64Matrix;
293 const int colCount(last-first);
294 const int featDim(
data.features.rows());
297 Matrix d(featDim-1, colCount);
299 for (
int i = 0; i < colCount; ++i)
301 d.col(i) =
data.features.block(0,
data.indices[first+i],featDim-1, 1);
302 t.col(i) =
data.times.col(
data.indices[first + i]);
304 const Vector box = d.rowwise().maxCoeff() - d.rowwise().minCoeff();
305 const std::int64_t timeBox = t.maxCoeff() - t.minCoeff();
307 const T boxDim(
box.maxCoeff());
309 if (boxDim > maxBoxDim || timeBox > maxTimeWindow)
311 data.unfitPointsCount += colCount;
314 const Vector mean = d.rowwise().sum() /
T(colCount);
315 const Matrix NN = (d.colwise() - mean);
317 const std::int64_t minTime = t.minCoeff();
318 const std::int64_t maxTime = t.maxCoeff();
319 const std::int64_t meanTime = t.sum() /
T(colCount);
322 const Matrix C(NN * NN.transpose());
323 Vector eigenVa = Vector::Identity(featDim-1, 1);
324 Matrix eigenVe = Matrix::Identity(featDim-1, featDim-1);
326 if(keepNormals || keepEigenValues || keepEigenVectors || keepCovariances || keepShapes || minPlanarity > 0)
328 if(C.fullPivHouseholderQr().rank()+1 >= featDim-1)
330 const Eigen::EigenSolver<Matrix> solver(C);
331 eigenVa = solver.eigenvalues().real();
332 eigenVe = solver.eigenvectors().real();
336 data.unfitPointsCount += colCount;
341 Eigen::Matrix<T, 3, 1> vals;
342 (vals << eigenVa(0),eigenVa(1),eigenVa(2));
343 vals = vals/eigenVa.sum();
344 const T planarity = 2 * vals(1)-2*vals(2);
346 if (planarity < minPlanarity)
348 data.unfitPointsCount += colCount;
355 Vector pointIds(1,colCount);
356 Matrix points(3,colCount);
360 for (
int i = 0; i < colCount; ++i)
362 pointIds(i) =
data.indices[first+i];
363 points.col(i) =
data.features.block(0,
data.indices[first+i],2, 1);
369 normal = computeNormal<T>(eigenVa, eigenVe);
373 density = computeDensity<T>(NN);
376 serialEigVector = serializeEigVec<T>(eigenVe);
379 serialCovVector = serializeEigVec<T>(C);
382 if(
data.descriptors.rows() != 0)
383 assert(
data.descriptors.cols() != 0);
386 if(samplingMethod == 0)
388 for(
int i=0; i<colCount; ++i)
390 const float r = (float)std::rand()/(float)RAND_MAX;
394 const int k =
data.indices[first+i];
396 data.indicesToKeep.push_back(k);
399 data.times(0, k) = minTime;
400 data.times(1, k) = maxTime;
401 data.times(2, k) = meanTime;
406 data.pointIds->col(k) = pointIds;
407 data.pointX->col(k) = points.row(0);
408 data.pointY->col(k) = points.row(1);
409 data.pointZ->col(k) = points.row(2);
410 (*
data.numOfNN)(0,k) = NN.cols();
413 data.normals->col(k) = normal;
415 (*
data.densities)(0,k) = density;
417 data.eigenValues->col(k) = eigenVa;
419 data.eigenVectors->col(k) = serialEigVector;
421 data.covariance->col(k) = serialCovVector;
423 data.means->col(k) = mean;
427 Eigen::Matrix<T, 3, 3> shapeMat;
428 (shapeMat << 0, 2, -2, 1, -1, 0, 0, 0, 3);
429 Eigen::Matrix<T, 3, 1> vals;
430 (vals << eigenVa(0),eigenVa(1),eigenVa(2));
431 vals = vals/eigenVa.sum();
432 data.shapes->col(k) = shapeMat * vals;
437 (*
data.weights)(0,k) = colCount;
444 const int k =
data.indices[first];
446 data.indicesToKeep.push_back(k);
447 data.features.col(k).topRows(featDim-1) = mean;
449 data.times(0, k) = minTime;
450 data.times(1, k) = maxTime;
451 data.times(2, k) = meanTime;
453 data.features(featDim-1, k) = 1;
455 if(
data.descriptors.rows() != 0)
458 if (averageExistingDescriptors)
460 Vector mergedDesc(Vector::Zero(
data.descriptors.rows()));
461 for (
int i = 0; i < colCount; ++i)
462 mergedDesc +=
data.descriptors.col(
data.indices[first+i]);
463 mergedDesc /=
T(colCount);
464 data.descriptors.col(k) = mergedDesc;
472 data.pointIds->col(k) = pointIds;
473 data.pointX->col(k) = points.row(0);
474 data.pointY->col(k) = points.row(1);
475 data.pointZ->col(k) = points.row(2);
478 data.normals->col(k) = normal;
480 (*
data.densities)(0,k) = density;
482 data.eigenValues->col(k) = eigenVa;
484 data.eigenVectors->col(k) = serialEigVector;
486 data.covariance->col(k) = serialCovVector;
488 data.means->col(k) = mean;
491 Eigen::Matrix<T, 3, 3> shapeMat;
492 (shapeMat << 0, 2, -2, 1, -1, 0, 0, 0, 3);
493 Eigen::Matrix<T, 3, 1> vals;
494 (vals << eigenVa(0),eigenVa(1),eigenVa(2));
495 vals = vals/eigenVa.sum();
496 data.shapes->col(k) = shapeMat * vals;
499 (*
data.weights)(0,k) = colCount;