Apollo 10.0
自动驾驶开放平台
apollo::perception::algorithm::PlaneFitGroundDetector类 参考

#include <i_ground.h>

类 apollo::perception::algorithm::PlaneFitGroundDetector 继承关系图:
apollo::perception::algorithm::PlaneFitGroundDetector 的协作图:

Public 成员函数

 PlaneFitGroundDetector (PlaneFitGroundDetectorParam &param)
 
 ~PlaneFitGroundDetector ()
 
bool Init ()
 
bool Detect (const float *point_cloud, float *height_above_ground, unsigned int nr_points, unsigned int nr_point_elements)
 
void ResetParams (float ori_z_lower, float ori_z_upper)
 
void UpdateParams (float parsing_ground_z, float buffer, double timestamp)
 
const char * GetLabel () const
 
const VoxelGridXY< float > * GetGrid () const
 
const GroundPlaneLiDAR * GetGroundPlane (int r, int c) const
 
unsigned int GetGridDimX () const
 
unsigned int GetGridDimY () const
 
float GetUnknownHeight ()
 
void Pc2Voxel (float x, float y, float z, int *row, int *col)
 
PlaneFitPointCandIndices ** GetCandis () const
 
- Public 成员函数 继承自 apollo::perception::algorithm::BaseGroundDetector
 BaseGroundDetector (PlaneFitGroundDetectorParam &param)
 
virtual ~BaseGroundDetector ()
 

Protected 成员函数

void CleanUp ()
 
void InitOrderTable (const VoxelGridXY< float > *vg, std::pair< int, int > *order)
 
int Fit ()
 
int FitLine (unsigned int r)
 
int FitGrid (const float *point_cloud, PlaneFitPointCandIndices *candi, GroundPlaneLiDAR *groundplane, unsigned int nr_points, unsigned int nr_point_element, float dist_thre)
 
int FitInOrder ()
 
int FilterCandidates (int r, int c, const float *point_cloud, PlaneFitPointCandIndices *candi, std::vector< std::pair< int, int > > *neighbors, unsigned int nr_point_element)
 
int FitGridWithNeighbors (int r, int c, const float *point_cloud, GroundPlaneLiDAR *groundplane, unsigned int nr_points, unsigned int nr_point_element, float dist_thre)
 
void GetNeighbors (int r, int c, int rows, int cols, std::vector< std::pair< int, int > > *neighbors)
 
float CalculateAngleDist (const GroundPlaneLiDAR &plane, const std::vector< std::pair< int, int > > &neighbors)
 
int Filter ()
 
int FilterLine (unsigned int r)
 
int FilterGrid (const Voxel< float > &vg, const float *point_cloud, PlaneFitPointCandIndices *candi, unsigned int nr_points, unsigned int nr_point_element)
 
int Smooth ()
 
int SmoothInOrder ()
 
void GetInliers (int *inliers)
 
void Optimization ()
 
void PlaneRefine ()
 
void SetGroundPlaneSpherParams (float *params)
 
void GetGroundPlaneSpherParams (float *params)
 
void SmoothInMath ()
 
int SmoothLine (unsigned int up, unsigned int r, unsigned int dn)
 
int CompleteGrid (const GroundPlaneSpherical &lt, const GroundPlaneSpherical &rt, const GroundPlaneSpherical &up, const GroundPlaneSpherical &dn, GroundPlaneSpherical *gp)
 
int SmoothGrid (const GroundPlaneSpherical &g, const GroundPlaneSpherical &lt, const GroundPlaneSpherical &rt, const GroundPlaneSpherical &up, const GroundPlaneSpherical &dn, GroundPlaneSpherical *gp)
 
int CompareZ (const float *point_cloud, const std::vector< int > &point_indices, const float *z_values, PlaneFitPointCandIndices *candi, unsigned int nr_points, unsigned int nr_point_element, unsigned int nr_compares)
 
void ComputeAdaptiveThreshold ()
 
void ComputeSignedGroundHeight (const float *point_cloud, float *height_above_ground, unsigned int nr_points, unsigned int nr_point_elements)
 
void ComputeSignedGroundHeightLine (const float *point_cloud, const GroundPlaneLiDAR *up, const GroundPlaneLiDAR *cn, const GroundPlaneLiDAR *dn, float *height_above_ground, unsigned int r, unsigned int nr_points, unsigned int nr_point_elements)
 

Protected 属性

VoxelGridXY< float > * vg_fine_
 
VoxelGridXY< float > * vg_coarse_
 
GroundPlaneLiDAR ** ground_planes_
 
GroundPlaneSpherical ** ground_planes_sphe_
 
PlaneFitPointCandIndices ** local_candis_
 
std::pair< float, bool > ** ground_z_
 
float ** pf_thresholds_
 
unsigned int * map_fine_to_coarse_
 
char * labels_
 
float * sampled_z_values_
 
float * pf_threeds_
 
float * spher_params_
 
int * sampled_indices_
 
int age_ = 0
 
std::pair< int, int > * order_table_
 
double frame_timestamp_ = 0.0
 
float ** weight_buffer_ = nullptr
 
int * inliers_ = nullptr
 
float * sphe_params_ = nullptr
 
std::vector< std::vector< unsigned int > > neighbors_
 
Eigen::SparseMatrix< float > a_array_
 
Eigen::SparseMatrix< float > b_array_
 
Eigen::SimplicialLDLT< Eigen::SparseMatrix< float > > solver_
 
- Protected 属性 继承自 apollo::perception::algorithm::BaseGroundDetector
PlaneFitGroundDetectorParam & param_
 

详细描述

在文件 i_ground.h 第 263 行定义.

构造及析构函数说明

◆ PlaneFitGroundDetector()

apollo::perception::algorithm::PlaneFitGroundDetector::PlaneFitGroundDetector ( PlaneFitGroundDetectorParam &  param)
explicit

在文件 i_ground.cc 第 104 行定义.

105 : BaseGroundDetector(param) {
106 assert(Init());
107}
BaseGroundDetector(PlaneFitGroundDetectorParam &param)
Definition i_ground.h:251

◆ ~PlaneFitGroundDetector()

apollo::perception::algorithm::PlaneFitGroundDetector::~PlaneFitGroundDetector ( )

在文件 i_ground.cc 第 109 行定义.

109 {
110 CleanUp();
111 if (weight_buffer_ != nullptr) {
112 IFree2<float>(&weight_buffer_);
113 }
114 if (inliers_ != nullptr) {
115 IFreeAligned<int>(&inliers_);
116 }
117 if (sphe_params_ != nullptr) {
118 IFreeAligned<float>(&sphe_params_);
119 }
120}

成员函数说明

◆ CalculateAngleDist()

float apollo::perception::algorithm::PlaneFitGroundDetector::CalculateAngleDist ( const GroundPlaneLiDAR &  plane,
const std::vector< std::pair< int, int > > &  neighbors 
)
protected

在文件 i_ground.cc 第 1067 行定义.

1069 {
1070 float angle_dist = 0.0f;
1071 int count = 0;
1072 unsigned int j = 0;
1073 int r_n = 0;
1074 int c_n = 0;
1075 for (j = 0; j < neighbors.size(); ++j) {
1076 r_n = neighbors[j].first;
1077 c_n = neighbors[j].second;
1078 if (ground_planes_[r_n][c_n].IsValid()) {
1079 angle_dist += calculate_two_angles(ground_planes_[r_n][c_n], plane);
1080 count++;
1081 }
1082 }
1083 if (count == 0) {
1084 return -1;
1085 }
1086 return angle_dist / static_cast<float>(count);
1087}
float calculate_two_angles(const GroundPlaneLiDAR &p1, const GroundPlaneLiDAR &p2)
Definition i_ground.cc:876

◆ CleanUp()

void apollo::perception::algorithm::PlaneFitGroundDetector::CleanUp ( )
protected

在文件 i_ground.cc 第 336 行定义.

336 {
337 if (vg_fine_) {
338 delete vg_fine_;
339 }
340 if (vg_coarse_) {
341 delete vg_coarse_;
342 }
343 IFree2<GroundPlaneLiDAR>(&ground_planes_);
344 IFree2<GroundPlaneSpherical>(&ground_planes_sphe_);
345 IFree2<std::pair<float, bool>>(&ground_z_);
346 IFree2<PlaneFitPointCandIndices>(&local_candis_);
347 IFreeAligned<float>(&pf_threeds_);
348 IFreeAligned<char>(&labels_);
349 IFreeAligned<unsigned int>(&map_fine_to_coarse_);
350 IFreeAligned<float>(&sampled_z_values_);
351 IFreeAligned<int>(&sampled_indices_);
352 IFree2<float>(&pf_thresholds_);
353 IFree<std::pair<int, int>>(&order_table_);
354}

◆ CompareZ()

int apollo::perception::algorithm::PlaneFitGroundDetector::CompareZ ( const float *  point_cloud,
const std::vector< int > &  point_indices,
const float *  z_values,
PlaneFitPointCandIndices *  candi,
unsigned int  nr_points,
unsigned int  nr_point_element,
unsigned int  nr_compares 
)
protected

在文件 i_ground.cc 第 356 行定义.

362 {
363 int pos = 0;
364 int nr_candis = 0;
365 unsigned int i = 0;
366 unsigned int nr_contradi = 0;
367 unsigned int nr_z_comp_fail_threshold =
368 IMin(param_.nr_z_comp_fail_threshold, (unsigned int)(nr_compares >> 1));
369 const float *ptr = nullptr;
370 float z = 0.0f;
371 float delta_z = 0.0f;
372 std::vector<int>::const_iterator iter = indices.cbegin();
373 while (iter < indices.cend()) {
374 nr_contradi = 0;
375 pos = *iter++;
376 assert(pos < static_cast<int>(nr_points));
377 nr_contradi = 0;
378 // requires the Z element to be in the third position, i.e., after X, Y
379 ptr = point_cloud + (pos * nr_point_element);
380 z = ptr[2];
381 // for near range check valid height
382 if (IAbs(ptr[0]) < param_.roi_near_rad &&
383 IAbs(ptr[1]) < param_.roi_near_rad) {
386 continue;
387 }
388 }
389 if (nr_compares > nr_z_comp_fail_threshold) {
390 for (i = 0; i < nr_compares; ++i) {
391 delta_z = IAbs(z_values[i] - z);
392 if (delta_z > param_.planefit_filter_threshold) {
393 nr_contradi++;
394 if (nr_contradi > nr_z_comp_fail_threshold) {
395 break;
396 }
397 }
398 }
399 }
400 if (nr_contradi <= nr_z_comp_fail_threshold) {
401 labels_[pos] = 1;
402 candi->PushIndex(pos);
403 nr_candis++;
404 }
405 }
406 return nr_candis;
407}

◆ CompleteGrid()

int apollo::perception::algorithm::PlaneFitGroundDetector::CompleteGrid ( const GroundPlaneSpherical &  lt,
const GroundPlaneSpherical &  rt,
const GroundPlaneSpherical &  up,
const GroundPlaneSpherical &  dn,
GroundPlaneSpherical *  gp 
)
protected

在文件 i_ground.cc 第 1251 行定义.

1255 {
1256 int supports[] = {0, 0, 0, 0};
1257 float weights[] = {0.f, 0.f, 0.f, 0.f};
1258 gp->ForceInvalid();
1259 supports[0] = lt.GetNrSupport();
1260 supports[1] = rt.GetNrSupport();
1261 supports[2] = up.GetNrSupport();
1262 supports[3] = dn.GetNrSupport();
1263 int support_sum = 0;
1264 support_sum = ISum4(supports);
1265 if (!support_sum) {
1266 return 0;
1267 }
1268 weights[0] =
1269 static_cast<float>(supports[0]) / static_cast<float>(support_sum);
1270 weights[1] =
1271 static_cast<float>(supports[1]) / static_cast<float>(support_sum);
1272 weights[2] =
1273 static_cast<float>(supports[2]) / static_cast<float>(support_sum);
1274 weights[3] =
1275 static_cast<float>(supports[3]) / static_cast<float>(support_sum);
1276 // weighted average:
1277 gp->theta = weights[0] * lt.theta + weights[1] * rt.theta +
1278 weights[2] * up.theta + weights[3] * dn.theta;
1279 gp->phi = weights[0] * lt.phi + weights[1] * rt.phi + weights[2] * up.phi +
1280 weights[3] * dn.phi;
1281 gp->d = weights[0] * lt.d + weights[1] * rt.d + weights[2] * up.d +
1282 weights[3] * dn.d;
1283 // compute average - diveided by 4, round to nearest int
1284 support_sum = IMax(((support_sum + 2) >> 2), 1);
1285 gp->SetNrSupport(support_sum);
1286 return 1;
1287}

◆ ComputeAdaptiveThreshold()

void apollo::perception::algorithm::PlaneFitGroundDetector::ComputeAdaptiveThreshold ( )
protected

在文件 i_ground.cc 第 409 行定义.

409 {
410 unsigned int r = 0;
411 unsigned int c = 0;
412 float dr = 0.0f;
413 float dc = 0.0f;
414 float k = 0.0f;
415 float b = 0.0f;
416 float min_dist = 0.0f;
417 float max_dist = 0.0f;
418 float thre = 0.0f;
419 float grid_rad = static_cast<float>(param_.nr_grids_coarse - 1) / 2;
420 assert(pf_thresholds_ != nullptr);
421 for (r = 0; r < param_.nr_grids_coarse; ++r) {
422 dr = static_cast<float>(r) - grid_rad;
423 dr *= dr;
424 for (c = 0; c < param_.nr_grids_coarse; ++c) {
425 dc = static_cast<float>(c) - grid_rad;
426 dc *= dc;
427 // store to center distance:
428 pf_thresholds_[r][c] = ISqrt(dr + dc);
429 }
430 }
433 &max_dist);
434 if (max_dist - min_dist < Constant<float>::EPSILON()) {
437 2;
438 for (r = 0; r < param_.nr_grids_coarse; ++r) {
439 for (c = 0; c < param_.nr_grids_coarse; ++c) {
440 pf_thresholds_[r][c] = thre;
441 }
442 }
443 } else {
446 k = k / (max_dist - min_dist);
449 b = (b - k * (min_dist + max_dist)) / 2;
450 for (r = 0; r < param_.nr_grids_coarse; ++r) {
451 for (c = 0; c < param_.nr_grids_coarse; ++c) {
452 thre = k * pf_thresholds_[r][c] + b;
453 pf_thresholds_[r][c] = thre;
454 }
455 }
456 }
457}
void IMinMaxElements(const T *a, int n, T *min_val, T *max_val)
Definition i_blas.h:3638

◆ ComputeSignedGroundHeight()

void apollo::perception::algorithm::PlaneFitGroundDetector::ComputeSignedGroundHeight ( const float *  point_cloud,
float *  height_above_ground,
unsigned int  nr_points,
unsigned int  nr_point_elements 
)
protected

在文件 i_ground.cc 第 459 行定义.

461 {
462 unsigned int r = 0;
463 unsigned int nm1 = param_.nr_grids_coarse - 1;
464 for (r = 0; r < nr_points; ++r) {
465 height_above_ground[r] = std::numeric_limits<float>::max();
466 }
468 point_cloud, ground_planes_[0], ground_planes_[0], ground_planes_[1],
469 height_above_ground, 0, nr_points, nr_point_elements);
470 for (r = 1; r < nm1; ++r) {
473 height_above_ground, r, nr_points,
474 nr_point_elements);
475 }
476 ComputeSignedGroundHeightLine(point_cloud, ground_planes_[nm1 - 1],
478 height_above_ground, nm1, nr_points,
479 nr_point_elements);
480}
void ComputeSignedGroundHeightLine(const float *point_cloud, const GroundPlaneLiDAR *up, const GroundPlaneLiDAR *cn, const GroundPlaneLiDAR *dn, float *height_above_ground, unsigned int r, unsigned int nr_points, unsigned int nr_point_elements)
Definition i_ground.cc:482

◆ ComputeSignedGroundHeightLine()

void apollo::perception::algorithm::PlaneFitGroundDetector::ComputeSignedGroundHeightLine ( const float *  point_cloud,
const GroundPlaneLiDAR *  up,
const GroundPlaneLiDAR *  cn,
const GroundPlaneLiDAR *  dn,
float *  height_above_ground,
unsigned int  r,
unsigned int  nr_points,
unsigned int  nr_point_elements 
)
protected

在文件 i_ground.cc 第 482 行定义.

486 {
487 unsigned int i = 0;
488 unsigned int c = 0;
489 unsigned int id = 0;
490 int pos = 0;
491 char label = 0;
492 const float *cptr = nullptr;
493 float dist[] = {0, 0, 0, 0, 0};
494 const float *plane[] = {nullptr, nullptr, nullptr, nullptr, nullptr};
495 float min_abs_dist = 0.0f;
496 unsigned int nm1 = param_.nr_grids_coarse - 1;
497 assert(param_.nr_grids_coarse >= 2);
498 plane[0] = cn[0].IsValid() ? cn[0].params : nullptr;
499 plane[1] = cn[1].IsValid() ? cn[1].params : nullptr;
500 plane[2] = up[0].IsValid() ? up[0].params : nullptr;
501 plane[3] = dn[0].IsValid() ? dn[0].params : nullptr;
502 std::vector<int>::const_iterator iter = (*vg_coarse_)(r, 0).indices_.cbegin();
503 while (iter < (*vg_coarse_)(r, 0).indices_.cend()) {
504 pos = *iter;
505 assert(pos < static_cast<int>(nr_points));
506 label = labels_[pos];
507 cptr = point_cloud + (nr_point_elements * pos);
508 dist[0] = plane[0] != nullptr
510 : std::numeric_limits<float>::max();
511 min_abs_dist = IAbs(dist[0]);
512 id = 0;
513 // for candidates we take min dist:
514 if (label) {
515 dist[1] = plane[1] != nullptr
517 : std::numeric_limits<float>::max();
518 dist[2] = plane[2] != nullptr
520 : std::numeric_limits<float>::max();
521 dist[3] = plane[3] != nullptr
523 : std::numeric_limits<float>::max();
524 for (i = 1; i < 4; ++i) {
525 if (min_abs_dist > IAbs(dist[i])) {
526 min_abs_dist = IAbs(dist[i]);
527 id = i;
528 }
529 }
530 }
531 height_above_ground[pos] = dist[id];
532 ++iter;
533 }
534
535 for (c = 1; c < nm1; ++c) {
536 plane[0] = cn[c].IsValid() ? cn[c].params : nullptr;
537 plane[1] = cn[c - 1].IsValid() ? cn[c - 1].params : nullptr;
538 plane[2] = cn[c + 1].IsValid() ? cn[c + 1].params : nullptr;
539 plane[3] = up[c].IsValid() ? up[c].params : nullptr;
540 plane[4] = dn[c].IsValid() ? dn[c].params : nullptr;
541 iter = (*vg_coarse_)(r, c).indices_.cbegin();
542 while (iter < (*vg_coarse_)(r, c).indices_.cend()) {
543 pos = *iter;
544 assert(pos < static_cast<int>(nr_points));
545 label = labels_[pos];
546 cptr = point_cloud + (nr_point_elements * pos);
547 dist[0] = plane[0] != nullptr
549 : std::numeric_limits<float>::max();
550 min_abs_dist = IAbs(dist[0]);
551 id = 0;
552 if (label) {
553 dist[1] = plane[1] != nullptr
555 : std::numeric_limits<float>::max();
556 dist[2] = plane[2] != nullptr
558 : std::numeric_limits<float>::max();
559 dist[3] = plane[3] != nullptr
561 : std::numeric_limits<float>::max();
562 dist[4] = plane[4] != nullptr
564 : std::numeric_limits<float>::max();
565 for (i = 1; i < 5; ++i) {
566 if (min_abs_dist > IAbs(dist[i])) {
567 min_abs_dist = IAbs(dist[i]);
568 id = i;
569 }
570 }
571 }
572 height_above_ground[pos] = dist[id];
573 ++iter;
574 }
575 }
576 plane[0] = cn[nm1].IsValid() ? cn[nm1].params : nullptr;
577 plane[1] = cn[nm1 - 1].IsValid() ? cn[nm1 - 1].params : nullptr;
578 plane[2] = up[nm1].IsValid() ? up[nm1].params : nullptr;
579 plane[3] = dn[nm1].IsValid() ? dn[nm1].params : nullptr;
580 iter = (*vg_coarse_)(r, nm1).indices_.cbegin();
581 while (iter < (*vg_coarse_)(r, nm1).indices_.cend()) {
582 pos = *iter;
583 assert(pos < static_cast<int>(nr_points));
584 label = labels_[pos];
585 cptr = point_cloud + (nr_point_elements * pos);
586 dist[0] = plane[0] != nullptr
588 : std::numeric_limits<float>::max();
589 min_abs_dist = IAbs(dist[0]);
590 id = 0;
591 // for candidates we take min dist:
592 if (label) {
593 dist[1] = plane[1] != nullptr
595 : std::numeric_limits<float>::max();
596 dist[2] = plane[2] != nullptr
598 : std::numeric_limits<float>::max();
599 dist[3] = plane[3] != nullptr
601 : std::numeric_limits<float>::max();
602 for (i = 1; i < 4; ++i) {
603 if (min_abs_dist > IAbs(dist[i])) {
604 min_abs_dist = IAbs(dist[i]);
605 id = i;
606 }
607 }
608 }
609 height_above_ground[pos] = dist[id];
610 ++iter;
611 }
612}
T IPlaneToPointSignedDistanceWUnitNorm(const T *pi, const T *p)
Definition i_plane.h:102
Definition future.h:29

◆ Detect()

bool apollo::perception::algorithm::PlaneFitGroundDetector::Detect ( const float *  point_cloud,
float *  height_above_ground,
unsigned int  nr_points,
unsigned int  nr_point_elements 
)
virtual

实现了 apollo::perception::algorithm::BaseGroundDetector.

在文件 i_ground.cc 第 1599 行定义.

1602 {
1603 assert(point_cloud != nullptr);
1604 assert(height_above_ground != nullptr);
1605 assert(nr_points <= param_.nr_points_max);
1606 assert(nr_point_elements >= 3);
1607 // setup the fine voxel grid
1608 if (!vg_fine_->SetS(point_cloud, nr_points, nr_point_elements)) {
1609 return false;
1610 }
1611 // setup the coarse voxel grid
1612 if (!vg_coarse_->SetS(point_cloud, nr_points, nr_point_elements)) {
1613 return false;
1614 }
1615
1616 // when single-frame-detect, should empty ground_planes_
1618 for (size_t row = 0; row < param_.nr_grids_coarse; ++row) {
1619 for (size_t col = 0; col < param_.nr_grids_coarse; ++col) {
1620 ground_planes_[row][col].ForceInvalid();
1622 }
1623 }
1624 }
1625 // int nr_candis = 0;
1626 // int nr_valid_grid = 0;
1627 unsigned int r = 0;
1628 unsigned int c = 0;
1629 // Filter to generate plane fitting candidates
1630 // int nr_candis =
1631 Filter();
1632 // std::cout << "# of plane candidates: " << nr_candis << std::endl;
1633 // Fit local plane using ransac
1634 // nr_valid_grid = Fit();
1635 // int nr_valid_grid =
1636 FitInOrder();
1637 // std::cout << "# of valid plane geometry (fitting): " << nr_valid_grid <<
1638 // std::endl;
1639 // Smooth plane using neighborhood information:
1641 SmoothInMath();
1642 } else {
1643 for (int iter = 0; iter < param_.nr_smooth_iter; ++iter) {
1644 // Smooth();
1645 SmoothInOrder();
1646 }
1647 }
1648
1649 for (r = 0; r < param_.nr_grids_coarse; ++r) {
1650 for (c = 0; c < param_.nr_grids_coarse; ++c) {
1651 if ((*vg_coarse_)(r, c).Empty()) {
1653 }
1654 }
1655 }
1656
1657 // std::cout << "# of valid plane geometry (Smooth): " << nr_valid_grid <<
1658 // std::endl;
1659 // compute point to ground distance
1660 ComputeSignedGroundHeight(point_cloud, height_above_ground, nr_points,
1661 nr_point_elements);
1662 return true;
1663}
void ComputeSignedGroundHeight(const float *point_cloud, float *height_above_ground, unsigned int nr_points, unsigned int nr_point_elements)
Definition i_ground.cc:459
bool SetS(const float *data, unsigned int nr_points, unsigned int nr_point_element)
Definition i_struct_s.h:747

◆ Filter()

int apollo::perception::algorithm::PlaneFitGroundDetector::Filter ( )
protected

在文件 i_ground.cc 第 669 行定义.

669 {
670 int nr_candis = 0;
671 unsigned int i = 0;
672 unsigned int r = 0;
673 memset(reinterpret_cast<void *>(labels_), 0,
674 vg_fine_->NrPoints() * sizeof(char));
675 // Clear candidate list
676 for (i = 0; i < vg_coarse_->NrVoxel(); ++i) {
677 local_candis_[0][i].Clear();
678 }
679 // Filter plane fitting candidates
680 for (r = 0; r < param_.nr_grids_fine; ++r) {
681 nr_candis += FilterLine(r);
682 }
683 return nr_candis;
684}

◆ FilterCandidates()

int apollo::perception::algorithm::PlaneFitGroundDetector::FilterCandidates ( int  r,
int  c,
const float *  point_cloud,
PlaneFitPointCandIndices *  candi,
std::vector< std::pair< int, int > > *  neighbors,
unsigned int  nr_point_element 
)
protected

在文件 i_ground.cc 第 836 行定义.

839 {
840 float avg_z = 0.f;
841 int count = 0;
842 unsigned int i = 0;
843 int r_n = 0;
844 int c_n = 0;
845 float z = 0.f;
846 std::vector<int> filtered_indices;
847 filtered_indices.reserve(candi->Size());
848 for (i = 0; i < neighbors->size(); ++i) {
849 r_n = (*neighbors)[i].first;
850 c_n = (*neighbors)[i].second;
851 if (ground_z_[r_n][c_n].second) {
852 avg_z += ground_z_[r_n][c_n].first;
853 count++;
854 }
855 }
856 if (count > 0) {
857 avg_z /= static_cast<float>(count);
858 ground_z_[r][c].first = avg_z;
859 ground_z_[r][c].second = true;
860 for (i = 0; i < candi->Size(); ++i) {
861 z = (point_cloud + (nr_point_element * (*candi)[i]))[2];
862 if (z > avg_z - param_.candidate_filter_threshold &&
864 filtered_indices.push_back((*candi)[i]);
865 } else {
866 labels_[(*candi)[i]] = 0;
867 }
868 }
869 if (filtered_indices.size() != candi->Size()) {
870 candi->indices.assign(filtered_indices.begin(), filtered_indices.end());
871 }
872 }
873 return count;
874}

◆ FilterGrid()

int apollo::perception::algorithm::PlaneFitGroundDetector::FilterGrid ( const Voxel< float > &  vg,
const float *  point_cloud,
PlaneFitPointCandIndices *  candi,
unsigned int  nr_points,
unsigned int  nr_point_element 
)
protected

在文件 i_ground.cc 第 614 行定义.

618 {
619 int pos = 0;
620 int rseed = I_DEFAULT_SEED;
621 int nr_candis = 0;
622 unsigned int i = 0;
623 unsigned int nr_samples = IMin(param_.nr_z_comp_candis, vx.NrPoints());
624 if (vx.Empty()) {
625 return 0;
626 }
627 // generate sampled indices
628 if (vx.NrPoints() <= param_.nr_z_comp_candis) {
629 // IRamp(sampled_indices_, vx.NrPoints());
630 // sampled z values
631 for (i = 0; i < vx.NrPoints(); ++i) {
632 pos = vx.indices_[i] * nr_point_element;
633 // requires the Z element to be in the third position, i.e., after X, Y
634 sampled_z_values_[i] = (point_cloud + pos)[2];
635 }
636 } else {
638 static_cast<int>(vx.NrPoints()), &rseed);
639 // sampled z values
640 for (i = 0; i < nr_samples; ++i) {
641 pos = vx.indices_[sampled_indices_[i]] * nr_point_element;
642 // requires the Z element to be in the third position, i.e., after X, Y
643 sampled_z_values_[i] = (point_cloud + pos)[2];
644 }
645 }
646 // Filter points and get plane fitting candidates
647 nr_candis = CompareZ(point_cloud, vx.indices_, sampled_z_values_, candi,
648 nr_points, nr_point_element, nr_samples);
649 return nr_candis;
650}
int CompareZ(const float *point_cloud, const std::vector< int > &point_indices, const float *z_values, PlaneFitPointCandIndices *candi, unsigned int nr_points, unsigned int nr_point_element, unsigned int nr_compares)
Definition i_ground.cc:356
void IRandomSample(int *sample, int n, int pool_size, int *s)
Definition i_rand.h:47

◆ FilterLine()

int apollo::perception::algorithm::PlaneFitGroundDetector::FilterLine ( unsigned int  r)
protected

在文件 i_ground.cc 第 652 行定义.

652 {
653 int nr_candis = 0;
654 unsigned int c = 0;
655 const float *point_cloud = vg_fine_->const_data();
656 unsigned int nr_points = vg_fine_->NrPoints();
657 unsigned int nr_point_element = vg_fine_->NrPointElement();
658 unsigned int begin = (r * param_.nr_grids_fine);
659 int parent = 0;
660 for (c = 0; c < param_.nr_grids_fine; c++) {
661 parent = map_fine_to_coarse_[begin + c];
662 nr_candis +=
663 FilterGrid((*vg_fine_)(r, c), point_cloud, &local_candis_[0][parent],
664 nr_points, nr_point_element);
665 }
666 return nr_candis;
667}
int FilterGrid(const Voxel< float > &vg, const float *point_cloud, PlaneFitPointCandIndices *candi, unsigned int nr_points, unsigned int nr_point_element)
Definition i_ground.cc:614

◆ Fit()

int apollo::perception::algorithm::PlaneFitGroundDetector::Fit ( )
protected

在文件 i_ground.cc 第 827 行定义.

827 {
828 int nr_grids = 0;
829 for (unsigned int r = 0; r < param_.nr_grids_coarse; ++r) {
830 nr_grids += FitLine(r);
831 }
832 return nr_grids;
833}

◆ FitGrid()

int apollo::perception::algorithm::PlaneFitGroundDetector::FitGrid ( const float *  point_cloud,
PlaneFitPointCandIndices *  candi,
GroundPlaneLiDAR *  groundplane,
unsigned int  nr_points,
unsigned int  nr_point_element,
float  dist_thre 
)
protected

在文件 i_ground.cc 第 686 行定义.

691 {
692 // initialize the best plane
693 groundplane->ForceInvalid();
694 // not enough samples, failed and return
695 if (candi->Size() < param_.nr_inliers_min_threshold) {
696 return 0;
697 }
698 GroundPlaneLiDAR plane;
699 float ptp_dist = 0.0f;
700 float fit_cost = 0.0f;
701 float fit_cost_best = dist_thre;
702 int nr_inliers = 0;
703 int nr_inliers_best = -1;
704 int i = 0;
705 int j = 0;
706 int rseed = I_DEFAULT_SEED;
707 int indices_trial[] = {0, 0, 0};
708 int nr_samples = candi->Prune(param_.nr_samples_min_threshold,
710 int nr_inliers_termi = IRound(static_cast<float>(nr_samples) *
712 // 3x3 matrix stores: x, y, z; x, y, z; x, y, z;
713 float samples[9];
714 // copy 3D points
715 float *psrc = nullptr;
716 float *pdst = pf_threeds_;
717 for (i = 0; i < nr_samples; ++i) {
718 assert((*candi)[i] < static_cast<int>(nr_points));
719 ICopy3(point_cloud + (nr_point_element * (*candi)[i]), pdst);
720 pdst += dim_point_;
721 }
722 // generate plane hypothesis and vote
723 for (i = 0; i < param_.nr_ransac_iter_threshold; ++i) {
724 IRandomSample(indices_trial, 3, nr_samples, &rseed);
725 IScale3(indices_trial, dim_point_);
726 ICopy3(pf_threeds_ + indices_trial[0], samples);
727 ICopy3(pf_threeds_ + indices_trial[1], samples + 3);
728 ICopy3(pf_threeds_ + indices_trial[2], samples + 6);
729 IPlaneFitDestroyed(samples, plane.params);
730 // check if the plane hypothesis has valid geometry
731 if (plane.GetDegreeNormalToZ() > param_.planefit_orien_threshold) {
732 continue;
733 }
734 // iterate samples and check if the point to plane distance is below
735 // threshold
736 psrc = pf_threeds_;
737 nr_inliers = 0;
738 fit_cost = 0;
739 for (j = 0; j < nr_samples; ++j) {
740 ptp_dist = IPlaneToPointDistanceWUnitNorm(plane.params, psrc);
741 if (ptp_dist < dist_thre) {
742 nr_inliers++;
743 fit_cost += ptp_dist;
744 }
745 psrc += dim_point_;
746 }
747 // Assign number of supports
748 plane.SetNrSupport(nr_inliers);
749
750 fit_cost = nr_inliers > 0 ? (fit_cost / static_cast<float>(nr_inliers))
751 : dist_thre;
752 // record the best plane
753 if (nr_inliers >= nr_inliers_best) {
754 if (nr_inliers == nr_inliers_best) {
755 if (fit_cost < fit_cost_best) {
756 nr_inliers_best = nr_inliers;
757 fit_cost_best = fit_cost;
758 *groundplane = plane;
759 }
760 } else {
761 nr_inliers_best = nr_inliers;
762 fit_cost_best = fit_cost;
763 *groundplane = plane;
764 }
765 // found enough inliers - terminate the ransac
766 if (nr_inliers_best > nr_inliers_termi) {
767 break;
768 }
769 }
770 }
771 // check if meet the inlier number requirement
772 if (!groundplane->IsValid()) {
773 return 0;
774 }
775 if (groundplane->GetNrSupport() <
776 static_cast<int>(param_.nr_inliers_min_threshold)) {
777 groundplane->ForceInvalid();
778 return 0;
779 }
780 // iterate samples and check if the point to plane distance is within
781 // threshold
782 nr_inliers = 0;
783 psrc = pf_threeds_;
784 pdst = pf_threeds_;
785 for (i = 0; i < nr_samples; ++i) {
786 ptp_dist = IPlaneToPointDistanceWUnitNorm(groundplane->params, psrc);
787 if (ptp_dist < dist_thre) {
788 ICopy3(psrc, pdst);
789 pdst += 3;
790 nr_inliers++;
791 }
792 psrc += dim_point_;
793 }
794 groundplane->SetNrSupport(nr_inliers);
795 // note that pf_threeds_ will be destroyed after calling this routine
796 IPlaneFitTotalLeastSquare(pf_threeds_, groundplane->params, nr_inliers);
797 // filtering: the best plane orientation is not valid*/
798 // std::cout << groundplane->GetDegreeNormalToZ() << std::endl;
799 if (groundplane->GetDegreeNormalToZ() > param_.planefit_orien_threshold) {
800 groundplane->ForceInvalid();
801 return 0;
802 }
803 return nr_inliers;
804}
void IPlaneFitDestroyed(T *Xs, T *pi)
Definition i_plane.h:447
void ICopy3(const T src[3], T dst[3])
Definition i_blas.h:40
T IPlaneToPointDistanceWUnitNorm(const T *pi, const T *p)
Definition i_plane.h:93
void IPlaneFitTotalLeastSquare(T *X, T *pi, int n)
Definition i_plane.h:140
void IScale3(T x[3], T sf)
Definition i_blas.h:1868

◆ FitGridWithNeighbors()

int apollo::perception::algorithm::PlaneFitGroundDetector::FitGridWithNeighbors ( int  r,
int  c,
const float *  point_cloud,
GroundPlaneLiDAR *  groundplane,
unsigned int  nr_points,
unsigned int  nr_point_element,
float  dist_thre 
)
protected

在文件 i_ground.cc 第 883 行定义.

885 {
886 // initialize the best plane
887 groundplane->ForceInvalid();
888 // not enough samples, failed and return
889
890 PlaneFitPointCandIndices &candi = local_candis_[r][c];
891 std::vector<std::pair<int, int>> neighbors;
893 &neighbors);
894 FilterCandidates(r, c, point_cloud, &candi, &neighbors, nr_point_element);
895
896 if (candi.Size() < param_.nr_inliers_min_threshold) {
897 return 0;
898 }
899
900 GroundPlaneLiDAR plane;
901 int kNr_iter =
902 param_.nr_ransac_iter_threshold + static_cast<int>(neighbors.size());
903 // check hypothesis initialized correct or not
904 if (kNr_iter < 1) {
905 return 0;
906 }
907 GroundPlaneLiDAR hypothesis[kNr_iter];
908
909 float ptp_dist = 0.0f;
910 int best = 0;
911 int nr_inliers = 0;
912 int nr_inliers_best = -1;
913 float angle_best = std::numeric_limits<float>::max();
914
915 int rseed = I_DEFAULT_SEED;
916 int indices_trial[] = {0, 0, 0};
917 int nr_samples = candi.Prune(param_.nr_samples_min_threshold,
919 int nr_inliers_termi = IRound(static_cast<float>(nr_samples) *
921 // 3x3 matrix stores: x, y, z; x, y, z; x, y, z;
922 float samples[9];
923 // copy 3D points
924 float *psrc = nullptr;
925 float *pdst = pf_threeds_;
926 int r_n = 0;
927 int c_n = 0;
928 float angle = -1.f;
929 for (int i = 0; i < nr_samples; ++i) {
930 assert(candi[i] < static_cast<int>(nr_points));
931 ICopy3(point_cloud + (nr_point_element * candi[i]), pdst);
932 pdst += dim_point_;
933 }
934 // generate plane hypothesis and vote
935 for (int i = 0; i < param_.nr_ransac_iter_threshold; ++i) {
936 IRandomSample(indices_trial, 3, nr_samples, &rseed);
937 IScale3(indices_trial, dim_point_);
938 ICopy3(pf_threeds_ + indices_trial[0], samples);
939 ICopy3(pf_threeds_ + indices_trial[1], samples + 3);
940 ICopy3(pf_threeds_ + indices_trial[2], samples + 6);
941 IPlaneFitDestroyed(samples, hypothesis[i].params);
942 // check if the plane hypothesis has valid geometry
943 if (hypothesis[i].GetDegreeNormalToZ() > param_.planefit_orien_threshold) {
944 continue;
945 }
946 // iterate samples and check if the point to plane distance is below
947 // threshold
948 psrc = pf_threeds_;
949 nr_inliers = 0;
950 for (int j = 0; j < nr_samples; ++j) {
951 ptp_dist = IPlaneToPointDistanceWUnitNorm(hypothesis[i].params, psrc);
952 if (ptp_dist < dist_thre) {
953 nr_inliers++;
954 }
955 psrc += dim_point_;
956 }
957 // Assign number of supports
958 hypothesis[i].SetNrSupport(nr_inliers);
959 hypothesis[i].SetOrigin(0);
960
961 if (nr_inliers > nr_inliers_termi) {
962 break;
963 }
964 }
965
966 for (size_t i = 0; i < neighbors.size(); ++i) {
967 r_n = neighbors[i].first;
968 c_n = neighbors[i].second;
969 if (ground_planes_[r_n][c_n].IsValid()) {
970 hypothesis[i + param_.nr_ransac_iter_threshold] =
971 ground_planes_[r_n][c_n];
972 psrc = pf_threeds_;
973 nr_inliers = 0;
974 for (int j = 0; j < nr_samples; ++j) {
976 hypothesis[i + param_.nr_ransac_iter_threshold].params, psrc);
977 if (ptp_dist < dist_thre) {
978 nr_inliers++;
979 }
980 psrc += dim_point_;
981 }
982 if (nr_inliers < static_cast<int>(param_.nr_inliers_min_threshold)) {
983 hypothesis[i + param_.nr_ransac_iter_threshold].ForceInvalid();
984 continue;
985 }
986 hypothesis[i + param_.nr_ransac_iter_threshold].SetNrSupport(nr_inliers);
987 hypothesis[i + param_.nr_ransac_iter_threshold].SetOrigin(1);
988 }
989 }
990
991 nr_inliers_best = -1;
992 for (int i = 0; i < kNr_iter; ++i) {
993 if (!(hypothesis[i].IsValid())) {
994 continue;
995 }
996 nr_inliers = hypothesis[i].GetNrSupport();
997 if (nr_inliers >= nr_inliers_best) {
998 if (nr_inliers == nr_inliers_best) {
999 angle = CalculateAngleDist(hypothesis[i], neighbors);
1000 if (angle < angle_best && angle > 0) {
1001 angle_best = angle;
1002 best = i;
1003 }
1004 } else {
1005 nr_inliers_best = nr_inliers;
1006 angle_best = CalculateAngleDist(hypothesis[i], neighbors);
1007 best = i;
1008 }
1009 }
1010 }
1011
1012 *groundplane = hypothesis[best];
1013
1014 // check if meet the inlier number requirement
1015 if (!groundplane->IsValid()) {
1016 groundplane->SetInvalidStatus(0);
1017 return 0;
1018 }
1019 if (groundplane->GetNrSupport() <
1020 static_cast<int>(param_.nr_inliers_min_threshold)) {
1021 groundplane->ForceInvalid();
1022 groundplane->SetInvalidStatus(1);
1023 return 0;
1024 }
1025 // iterate samples and check if the point to plane distance is within
1026 // threshold
1027 nr_inliers = 0;
1028 psrc = pf_threeds_;
1029 pdst = pf_threeds_;
1030 for (int i = 0; i < nr_samples; ++i) {
1031 ptp_dist = IPlaneToPointDistanceWUnitNorm(groundplane->params, psrc);
1032 if (ptp_dist < dist_thre) {
1033 ICopy3(psrc, pdst);
1034 pdst += 3;
1035 nr_inliers++;
1036 }
1037 psrc += dim_point_;
1038 }
1039 groundplane->SetNrSupport(nr_inliers);
1040
1041 // note that pf_threeds_ will be destroyed after calling this routine
1042 IPlaneFitTotalLeastSquare(pf_threeds_, groundplane->params, nr_inliers);
1043 if (angle_best <= CalculateAngleDist(*groundplane, neighbors)) {
1044 *groundplane = hypothesis[best];
1045 groundplane->SetStatus(true);
1046 }
1047
1048 if (groundplane->GetDegreeNormalToZ() > param_.planefit_orien_threshold) {
1049 groundplane->ForceInvalid();
1050 groundplane->SetInvalidStatus(2);
1051 return 0;
1052 }
1053
1054 const auto &voxel_cur = (*vg_coarse_)(r, c);
1055 float radius = voxel_cur.dim_x_ * 0.5f;
1056 float cx = voxel_cur.v_[0] + radius;
1057 float cy = voxel_cur.v_[1] + radius;
1058 float cz = -(groundplane->params[0] * cx + groundplane->params[1] * cy +
1059 groundplane->params[3]) /
1060 groundplane->params[2];
1061 ground_z_[r][c].first = cz;
1062 ground_z_[r][c].second = true;
1063
1064 return nr_inliers;
1065}
float CalculateAngleDist(const GroundPlaneLiDAR &plane, const std::vector< std::pair< int, int > > &neighbors)
Definition i_ground.cc:1067
void GetNeighbors(int r, int c, int rows, int cols, std::vector< std::pair< int, int > > *neighbors)
Definition i_ground.cc:1176
int FilterCandidates(int r, int c, const float *point_cloud, PlaneFitPointCandIndices *candi, std::vector< std::pair< int, int > > *neighbors, unsigned int nr_point_element)
Definition i_ground.cc:836

◆ FitInOrder()

int apollo::perception::algorithm::PlaneFitGroundDetector::FitInOrder ( )
protected

在文件 i_ground.cc 第 1089 行定义.

1089 {
1090 int nr_grids = 0;
1091 unsigned int i = 0;
1092 unsigned int j = 0;
1093 int r = 0;
1094 int c = 0;
1095 GroundPlaneLiDAR gp;
1096 for (i = 0; i < param_.nr_grids_coarse; ++i) {
1097 for (j = 0; j < param_.nr_grids_coarse; ++j) {
1098 ground_z_[i][j].first = 0.f;
1099 ground_z_[i][j].second = false;
1100 }
1101 }
1102 std::stringstream sstr;
1103 sstr << "[GroundFitInfo] " << std::to_string(frame_timestamp_) << std::endl;
1104 size_t count = 0;
1105 for (i = 0; i < vg_coarse_->NrVoxel(); ++i) {
1106 r = order_table_[i].first;
1107 c = order_table_[i].second;
1108
1109 if (param_.debug_output) {
1110 sstr << "[FitInOrder] row = " << r << " col = " << c
1111 << " center_x = "
1112 << (*vg_coarse_)(r, c).v_[0] + (*vg_coarse_)(r, c).dim_x_ * 0.5f
1113 << " center_y = "
1114 << (*vg_coarse_)(r, c).v_[1] + (*vg_coarse_)(r, c).dim_y_ * 0.5f
1115 << " inliers_thres = " << pf_thresholds_[r][c]
1116 << " [AfterFilterCandidates] count = " << local_candis_[r][c].Size();
1117
1118 float max_z = -5.0, min_z = 5.0;
1119 for (unsigned int p = 0; p < local_candis_[r][c].Size(); ++p) {
1120 float x = (vg_coarse_->const_data() +
1121 (vg_coarse_->NrPointElement() * (local_candis_[r][c])[p]))[0];
1122 float y = (vg_coarse_->const_data() +
1123 (vg_coarse_->NrPointElement() * (local_candis_[r][c])[p]))[1];
1124 float z = (vg_coarse_->const_data() +
1125 (vg_coarse_->NrPointElement() * (local_candis_[r][c])[p]))[2];
1126 if (z > max_z) {
1127 max_z = z;
1128 }
1129 if (z < min_z) {
1130 min_z = z;
1131 }
1132 if (p == 0) {
1133 sstr << " sample_point_cooridinate = (" << x << ", " << y
1134 << ", " << z << ")";
1135 }
1136 }
1137 sstr << " min_z = " << min_z << " max_z= " << max_z;
1138 }
1139 count += local_candis_[r][c].Size();
1141 r, c, vg_coarse_->const_data(), &gp, vg_coarse_->NrPoints(),
1143 static_cast<int>(param_.nr_inliers_min_threshold)) {
1145 ground_planes_[r][c] = gp;
1146 nr_grids++;
1147 } else {
1150 }
1151
1152 if (param_.debug_output) {
1153 sstr << " [AfterNeighborFilter] count = " << local_candis_[r][c].Size()
1154 << " [AfterGridPlaneFit] ground_z_valid = " << ground_z_[r][c].second
1155 << " ground_z_value = " << ground_z_[r][c].first
1156 << " plane_valid = " << ground_planes_[r][c].IsValid()
1157 << " plane_invalid_status = "
1159 << " plane_origin = " << ground_planes_[r][c].GetOrigin()
1160 << " support_number = " << ground_planes_[r][c].GetNrSupport()
1161 << " plane_params = " << ground_planes_[r][c].params[0] << ", "
1162 << ground_planes_[r][c].params[1] << ", "
1163 << ground_planes_[r][c].params[2]
1164 << ", " << ground_planes_[r][c].params[3] << std::endl;
1165 }
1166 }
1167 if (param_.debug_output) {
1168 AINFO << sstr.str();
1169 AINFO << "This Frame " << std::to_string(frame_timestamp_)
1170 << " ground_count is " << count;
1171 }
1172 sstr.clear();
1173 return nr_grids;
1174}
int FitGridWithNeighbors(int r, int c, const float *point_cloud, GroundPlaneLiDAR *groundplane, unsigned int nr_points, unsigned int nr_point_element, float dist_thre)
Definition i_ground.cc:883
#define AINFO
Definition log.h:42
void IPlaneEucliToSpher(const GroundPlaneLiDAR &src, GroundPlaneSpherical *dst)
Definition i_ground.cc:1717

◆ FitLine()

int apollo::perception::algorithm::PlaneFitGroundDetector::FitLine ( unsigned int  r)
protected

在文件 i_ground.cc 第 806 行定义.

806 {
807 int nr_grids = 0;
808 unsigned int c = 0;
809 GroundPlaneLiDAR gp;
810 for (c = 0; c < param_.nr_grids_coarse; c++) {
811 if (FitGrid(vg_coarse_->const_data(), &local_candis_[r][c], &gp,
813 pf_thresholds_[r][c]) >=
814 static_cast<int>(param_.nr_inliers_min_threshold)) {
815 // transform to polar coordinates and store:
817 ground_planes_[r][c] = gp;
818 nr_grids++;
819 } else {
822 }
823 }
824 return nr_grids;
825}
int FitGrid(const float *point_cloud, PlaneFitPointCandIndices *candi, GroundPlaneLiDAR *groundplane, unsigned int nr_points, unsigned int nr_point_element, float dist_thre)
Definition i_ground.cc:686

◆ GetCandis()

PlaneFitPointCandIndices ** apollo::perception::algorithm::PlaneFitGroundDetector::GetCandis ( ) const

在文件 i_ground.cc 第 1713 行定义.

1713 {
1714 return local_candis_;
1715}

◆ GetGrid()

const VoxelGridXY< float > * apollo::perception::algorithm::PlaneFitGroundDetector::GetGrid ( ) const

在文件 i_ground.cc 第 1690 行定义.

1690 {
1691 return vg_coarse_;
1692}

◆ GetGridDimX()

unsigned int apollo::perception::algorithm::PlaneFitGroundDetector::GetGridDimX ( ) const

在文件 i_ground.cc 第 1701 行定义.

1701 {
1702 return vg_coarse_->NrVoxelX();
1703}

◆ GetGridDimY()

unsigned int apollo::perception::algorithm::PlaneFitGroundDetector::GetGridDimY ( ) const

在文件 i_ground.cc 第 1705 行定义.

1705 {
1706 return vg_coarse_->NrVoxelY();
1707}

◆ GetGroundPlane()

const GroundPlaneLiDAR * apollo::perception::algorithm::PlaneFitGroundDetector::GetGroundPlane ( int  r,
int  c 
) const

在文件 i_ground.cc 第 1694 行定义.

1695 {
1696 assert(r >= 0 && r < static_cast<int>(param_.nr_grids_coarse));
1697 assert(c >= 0 && c < static_cast<int>(param_.nr_grids_coarse));
1698 return ground_planes_ != nullptr ? ground_planes_[r] + c : nullptr;
1699}

◆ GetGroundPlaneSpherParams()

void apollo::perception::algorithm::PlaneFitGroundDetector::GetGroundPlaneSpherParams ( float *  params)
protected

在文件 i_ground.cc 第 1512 行定义.

1512 {
1513 unsigned int lap_size = param_.nr_grids_coarse * param_.nr_grids_coarse;
1514 unsigned int offset = 0;
1515 // for (unsigned int r = 0; r < param_.nr_grids_coarse; ++r) {
1516 // for (unsigned int c = 0; c < param_.nr_grids_coarse; ++c) {
1517 // if ((*vg_coarse_)(r, c).Empty()) {
1518 // ground_planes_sphe_[r][c].ForceInvalid();
1519 // } else {
1520 // IPlaneEucliToSpher(ground_planes_[r][c],
1521 // &ground_planes_sphe_[r][c]);
1522 // }
1523 // }
1524 // }
1525 for (unsigned int i = 0; i < lap_size; ++i) {
1526 params[i + offset] = ground_planes_sphe_[0][i].theta;
1527 }
1528 offset += lap_size;
1529 for (unsigned int i = 0; i < lap_size; ++i) {
1530 params[i + offset] = ground_planes_sphe_[0][i].phi;
1531 }
1532 offset += lap_size;
1533 for (unsigned int i = 0; i < lap_size; ++i) {
1534 params[i + offset] = ground_planes_sphe_[0][i].d;
1535 }
1536}

◆ GetInliers()

void apollo::perception::algorithm::PlaneFitGroundDetector::GetInliers ( int *  inliers)
protected

在文件 i_ground.cc 第 1396 行定义.

1396 {
1397 unsigned int lap_size = param_.nr_grids_coarse * param_.nr_grids_coarse;
1398 for (unsigned int i = 0; i < lap_size; ++i) {
1399 inliers[i] = ground_planes_sphe_[0][i].GetNrSupport();
1400 }
1401}

◆ GetLabel()

const char * apollo::perception::algorithm::PlaneFitGroundDetector::GetLabel ( ) const

在文件 i_ground.cc 第 1665 行定义.

1665{ return labels_; }

◆ GetNeighbors()

void apollo::perception::algorithm::PlaneFitGroundDetector::GetNeighbors ( int  r,
int  c,
int  rows,
int  cols,
std::vector< std::pair< int, int > > *  neighbors 
)
protected

在文件 i_ground.cc 第 1176 行定义.

1178 {
1179 int left = IMax(0, c - 1);
1180 int right = IMin(cols - 1, c + 1);
1181 int up = IMax(0, r - 1);
1182 int down = IMin(rows - 1, r + 1);
1183 int x = 0;
1184 int y = 0;
1185 neighbors->reserve(8);
1186 for (x = left; x <= right; ++x) {
1187 for (y = up; y <= down; ++y) {
1188 if (x == c && y == r) {
1189 continue;
1190 }
1191 neighbors->push_back(std::pair<int, int>(y, x));
1192 }
1193 }
1194}

◆ GetUnknownHeight()

float apollo::perception::algorithm::PlaneFitGroundDetector::GetUnknownHeight ( )

在文件 i_ground.cc 第 1709 行定义.

1709 {
1710 return std::numeric_limits<float>::max();
1711}

◆ Init()

bool apollo::perception::algorithm::PlaneFitGroundDetector::Init ( )

在文件 i_ground.cc 第 152 行定义.

152 {
153 unsigned int r = 0;
154 unsigned int c = 0;
155 unsigned int pr = 0;
156 unsigned int pc = 0;
157 unsigned int index = 0;
158 unsigned int capacity = 0;
159 unsigned int sf = param_.nr_grids_fine / param_.nr_grids_coarse;
160 if (!param_.Validate()) {
161 return false;
162 }
163 // fine grid:
164 vg_fine_ = new VoxelGridXY<float>();
165 if (vg_fine_ == nullptr) {
166 return false;
167 }
172 return false;
173 }
174 // coarse grid:
175 vg_coarse_ = new VoxelGridXY<float>();
176 if (vg_coarse_ == nullptr) {
177 return false;
178 }
183 return false;
184 }
185
186 // Init order lookup table
187 order_table_ = IAlloc<std::pair<int, int>>(vg_fine_->NrVoxel());
189
190 // ground plane:
192 IAlloc2<GroundPlaneLiDAR>(param_.nr_grids_coarse, param_.nr_grids_coarse);
193 if (!ground_planes_) {
194 return false;
195 }
196 ground_planes_sphe_ = IAlloc2<GroundPlaneSpherical>(param_.nr_grids_coarse,
198 if (!ground_planes_sphe_) {
199 return false;
200 }
201 ground_z_ = IAlloc2<std::pair<float, bool>>(param_.nr_grids_coarse,
203 if (!ground_z_) {
204 return false;
205 }
206 // sample candis:
207 local_candis_ = IAlloc2<PlaneFitPointCandIndices>(param_.nr_grids_coarse,
209 if (!local_candis_) {
210 return false;
211 }
212 // Reserve space to avoid runtime memory re-allocation
213 for (r = 0; r < param_.nr_grids_coarse; ++r) {
214 for (c = 0; c < param_.nr_grids_coarse; ++c) {
215 if (r < (param_.nr_grids_coarse << 3) &&
216 c < (param_.nr_grids_coarse << 3)) {
217 capacity = 16384;
218 } else if (r < (param_.nr_grids_coarse << 2) &&
219 c < (param_.nr_grids_coarse << 2)) {
220 capacity = 8192;
221 } else if (r < (param_.nr_grids_coarse << 1) &&
222 c < (param_.nr_grids_coarse << 1)) {
223 capacity = 4096;
224 } else {
225 capacity = 512;
226 }
227 local_candis_[r][c].Reserve(capacity);
228 }
229 }
230 // threeds in ransac, in inhomogeneous coordinates:
232 IAllocAligned<float>(param_.nr_samples_max_threshold * dim_point_, 4);
233 if (!pf_threeds_) {
234 return false;
235 }
236 memset(reinterpret_cast<void *>(pf_threeds_), 0,
237 param_.nr_samples_max_threshold * dim_point_ * sizeof(float));
238 // labels:
239 labels_ = IAllocAligned<char>(param_.nr_points_max, 4);
240 if (!labels_) {
241 return false;
242 }
243 memset(reinterpret_cast<void *>(labels_), 0,
244 param_.nr_points_max * sizeof(char));
245 // map of fine grid id to coarse id:
246 map_fine_to_coarse_ = IAllocAligned<unsigned int>(
248 if (!map_fine_to_coarse_) {
249 return false;
250 }
251 for (r = 0; r < param_.nr_grids_fine; ++r) {
252 pr = r / sf;
253 index = r * param_.nr_grids_fine;
254 for (c = 0; c < param_.nr_grids_fine; ++c) {
255 pc = c / sf;
256 map_fine_to_coarse_[index + c] = pr * param_.nr_grids_coarse + pc;
257 }
258 }
259 // ransac memory:
260 sampled_z_values_ = IAllocAligned<float>(param_.nr_z_comp_candis, 4);
261 if (!sampled_z_values_) {
262 return false;
263 }
264 memset(reinterpret_cast<void *>(sampled_z_values_), 0,
265 param_.nr_z_comp_candis * sizeof(float));
266 // ransac memory:
267 sampled_indices_ = IAllocAligned<int>(param_.nr_z_comp_candis, 4);
268 if (!sampled_indices_) {
269 return false;
270 }
271 memset(reinterpret_cast<void *>(sampled_indices_), 0,
272 param_.nr_z_comp_candis * sizeof(int));
273 // ransac thresholds:
276 if (!pf_thresholds_) {
277 return false;
278 }
279 // compute thresholds
281
282 //global optimization
283 unsigned int lap_size = param_.nr_grids_coarse * param_.nr_grids_coarse;
284 neighbors_.resize(lap_size);
285 for (unsigned int r = 0; r < param_.nr_grids_coarse; ++r) {
286 for (unsigned int c = 0; c < param_.nr_grids_coarse; ++c) {
287 unsigned int index_cur = r * param_.nr_grids_coarse + c;
288 neighbors_[index_cur].clear();
289 if (r > 0) {
290 neighbors_[index_cur].push_back((r - 1)* param_.nr_grids_coarse + c);
291 }
292 if (r + 1 < param_.nr_grids_coarse) {
293 neighbors_[index_cur].push_back((r + 1)* param_.nr_grids_coarse + c);
294 }
295 if (c > 0) {
296 neighbors_[index_cur].push_back(r * param_.nr_grids_coarse + c - 1);
297 }
298 if (c + 1 < param_.nr_grids_coarse) {
299 neighbors_[index_cur].push_back(r * param_.nr_grids_coarse + c + 1);
300 }
301 if (c + 1 < param_.nr_grids_coarse && r + 1 < param_.nr_grids_coarse) {
302 neighbors_[index_cur].push_back(
303 (r + 1)* param_.nr_grids_coarse + c + 1);
304 }
305 if (c > 0 && r + 1 < param_.nr_grids_coarse) {
306 neighbors_[index_cur].push_back(
307 (r + 1)* param_.nr_grids_coarse + c - 1);
308 }
309 if (c + 1 < param_.nr_grids_coarse && r > 0) {
310 neighbors_[index_cur].push_back(
311 (r - 1)* param_.nr_grids_coarse + c + 1);
312 }
313 if (c > 0 && r > 0) {
314 neighbors_[index_cur].push_back(
315 (r - 1)* param_.nr_grids_coarse + c - 1);
316 }
317 }
318 }
319 weight_buffer_ = IAlloc2<float>(2, lap_size);
320 inliers_ = IAllocAligned<int>(lap_size, 4);
321 sphe_params_ = IAllocAligned<float>(lap_size * 3, 4);
322 a_array_.resize(lap_size * 2, lap_size);
323 b_array_.resize(lap_size * 2, 3);
324
325 for (unsigned int i = 0; i < lap_size; ++i) {
326 a_array_.coeffRef(i, i) = 1.0;
327 float w = -1.0 / neighbors_[i].size();
328 for (const auto& j : neighbors_[i]) {
329 a_array_.coeffRef(i, j) = w;
330 }
331 }
332
333 return true;
334}
void InitOrderTable(const VoxelGridXY< float > *vg, std::pair< int, int > *order)
Definition i_ground.cc:123
std::vector< std::vector< unsigned int > > neighbors_
Definition i_ground.h:367
bool Alloc(unsigned int nr_voxel_x, unsigned int nr_voxel_y, T spatial_bound_x_min, T spatial_bound_x_max, T spatial_bound_y_min, T spatial_bound_y_max, T spatial_bound_z_min, T spatial_bound_z_max)
Definition i_struct_s.h:634

◆ InitOrderTable()

void apollo::perception::algorithm::PlaneFitGroundDetector::InitOrderTable ( const VoxelGridXY< float > *  vg,
std::pair< int, int > *  order 
)
protected

在文件 i_ground.cc 第 123 行定义.

124 {
125 std::vector<std::pair<float, int>> map_dist;
126 float cx = 0.f;
127 float cy = 0.f;
128 float dist2 = 0.f;
129 float radius = 0.f;
130 unsigned int i = 0;
131 int id = 0;
132 for (i = 0; i < vg->NrVoxel(); ++i) {
133 const auto &voxel = vg->GetConstVoxels()[i];
134 radius = voxel.dim_x_ * 0.5f;
135 cx = voxel.v_[0] + radius;
136 cy = voxel.v_[1] + radius;
137 dist2 = cx * cx + cy * cy;
138 map_dist.push_back(std::pair<float, int>(dist2, i));
139 }
140 sort(map_dist.begin(), map_dist.end(),
141 [](const std::pair<float, int> &a, const std::pair<float, int> &b) {
142 return a.first < b.first;
143 });
144 for (i = 0; i < map_dist.size(); ++i) {
145 id = map_dist[i].second;
146 const auto &voxel = vg->GetConstVoxels()[id];
147 order[i].first = voxel.iy_;
148 order[i].second = voxel.ix_;
149 }
150}
const std::vector< Voxel< T > > & GetConstVoxels() const
Definition i_struct_s.h:370

◆ Optimization()

void apollo::perception::algorithm::PlaneFitGroundDetector::Optimization ( )
protected

在文件 i_ground.cc 第 1403 行定义.

1403 {
1404 unsigned int lap_size = param_.nr_grids_coarse * param_.nr_grids_coarse;
1405 unsigned int i = 0;
1406 Eigen::SparseMatrix<float> in;
1407 Eigen::SparseMatrix<float> out;
1408 memset((void*)weight_buffer_[0], 0, 2 * lap_size * sizeof(float));
1409
1410 for (i = 0; i < lap_size; ++i) {
1411 weight_buffer_[0][i] = inliers_[i] > 8 ?
1412 std::exp((inliers_[i] - 8) / 20) : 0.1;
1413 }
1414
1415 for (i = 0; i < lap_size; ++i) {
1416 for (const auto& j : neighbors_[i]) {
1417 weight_buffer_[1][i] += weight_buffer_[0][j];
1418 }
1419 }
1420
1421 for (i = 0; i < lap_size; ++i) {
1422 if (inliers_[i] > 0) {
1423 a_array_.coeffRef(i + lap_size, i) = weight_buffer_[0][i];
1424 } else {
1425 a_array_.coeffRef(i + lap_size, i) = 0.0;
1426 }
1427 for (const auto& j : neighbors_[i]) {
1428 // -weight_buffer_[0][j] / weight_buffer_[1][i]
1429 a_array_.coeffRef(i, j) = -1.0 / neighbors_[i].size();
1430 }
1431 }
1432
1433 a_array_.makeCompressed();
1434 solver_.compute(a_array_.transpose() * a_array_);
1435
1436 for (i = 0; i < lap_size; ++i) {
1437 if (inliers_[i] > 0) {
1438 b_array_.coeffRef(i + lap_size, 0) =
1439 sphe_params_[i] * weight_buffer_[0][i];
1440 b_array_.coeffRef(i + lap_size, 1) =
1441 sphe_params_[i + lap_size] * weight_buffer_[0][i];
1442 b_array_.coeffRef(i + lap_size, 2) =
1443 sphe_params_[i + lap_size * 2] * weight_buffer_[0][i];
1444 } else {
1445 b_array_.coeffRef(i + lap_size, 0) = 0.0;
1446 b_array_.coeffRef(i + lap_size, 1) = 0.0;
1447 b_array_.coeffRef(i + lap_size, 2) = 0.0;
1448 }
1449 }
1450 in = a_array_.transpose() * b_array_;
1451 out = solver_.solve(in);
1452 for (i = 0; i < lap_size; ++i) {
1453 sphe_params_[i] = out.coeffRef(i, 0);
1454 sphe_params_[i + lap_size] = out.coeffRef(i, 1);
1455 sphe_params_[i + lap_size * 2] = out.coeffRef(i, 2);
1456 }
1457}
Eigen::SimplicialLDLT< Eigen::SparseMatrix< float > > solver_
Definition i_ground.h:370

◆ Pc2Voxel()

void apollo::perception::algorithm::PlaneFitGroundDetector::Pc2Voxel ( float  x,
float  y,
float  z,
int *  row,
int *  col 
)

在文件 i_ground.cc 第 1667 行定义.

1667 {
1668 *row = -1;
1669 *col = -1;
1670 // points that are outside the defined BBOX are ignored
1671 if (x < -param_.roi_region_rad_x || x > param_.roi_region_rad_x ||
1672 y < -param_.roi_region_rad_y || y > param_.roi_region_rad_y ||
1673 z < -param_.roi_region_rad_z || z > param_.roi_region_rad_z) {
1674 return;
1675 }
1676
1677 float voxel_width_x = IDiv(param_.roi_region_rad_x +
1678 param_.roi_region_rad_x, static_cast<int>(param_.nr_grids_coarse));
1679 float voxel_width_y = IDiv(param_.roi_region_rad_y +
1680 param_.roi_region_rad_y, static_cast<int>(param_.nr_grids_coarse));
1681 float voxel_width_x_rec = IRec(voxel_width_x);
1682 float voxel_width_y_rec = IRec(voxel_width_y);
1683 int grid_size = param_.nr_grids_coarse;
1684 *col = IMin(grid_size - 1, static_cast<int>(
1685 (x + param_.roi_region_rad_x) * voxel_width_x_rec));
1686 *row = IMin(grid_size - 1, static_cast<int>(
1687 (y + param_.roi_region_rad_y) * voxel_width_y_rec));
1688}
float IDiv(float a, float b)
Definition i_basic.h:35

◆ PlaneRefine()

void apollo::perception::algorithm::PlaneFitGroundDetector::PlaneRefine ( )
protected

在文件 i_ground.cc 第 1459 行定义.

1459 {
1460 const float *point_cloud = vg_coarse_->const_data();
1461 unsigned int nr_point_element = vg_coarse_->NrPointElement();
1462 unsigned int nr_points = vg_coarse_->NrPoints();
1463 unsigned int r = 0;
1464 unsigned int c = 0;
1465 float dist_thre = 0.0;
1466 float ptp_dist = 0.0;
1467 int nr_inliers = 0;
1468 unsigned int i = 0;
1469 float threshold_rad = 5.0 * Constant<float>::DEGREE_TO_RADIAN();
1470 for (r = 0; r < param_.nr_grids_coarse; ++r) {
1471 for (c = 0; c < param_.nr_grids_coarse; ++c) {
1472 if ((*vg_coarse_)(r, c).Empty()) {
1473 continue;
1474 }
1475 dist_thre = pf_thresholds_[r][c];
1476 const auto& opt_gd = ground_planes_[r][c];
1477 GroundPlaneLiDAR fit_gd;
1478 PlaneFitPointCandIndices &candi = local_candis_[r][c];
1479 if (candi.Size() < param_.nr_inliers_min_threshold) {
1480 continue;
1481 }
1482 int nr_samples = candi.Prune(param_.nr_samples_min_threshold,
1484
1485 float *psrc = pf_threeds_;
1486 nr_inliers = 0;
1487 for (i = 0; i < nr_samples; ++i) {
1488 assert(candi[i] < (int)nr_points);
1489 ICopy3(point_cloud + (nr_point_element * candi[i]), psrc);
1490 ptp_dist = IPlaneToPointDistanceWUnitNorm(opt_gd.params, psrc);
1491 if (ptp_dist < dist_thre) {
1492 psrc += dim_point_;
1493 nr_inliers++;
1494 }
1495 }
1496 if (nr_inliers < param_.nr_inliers_min_threshold) {
1497 continue;
1498 }
1499 IPlaneFitTotalLeastSquare(pf_threeds_, fit_gd.params, nr_inliers);
1500 float angle = calculate_two_angles(opt_gd, fit_gd);
1501 if (angle > threshold_rad) {
1502 continue;
1503 }
1504 ground_planes_[r][c].params[0] = fit_gd.params[0];
1505 ground_planes_[r][c].params[1] = fit_gd.params[1];
1506 ground_planes_[r][c].params[2] = fit_gd.params[2];
1507 ground_planes_[r][c].params[3] = fit_gd.params[3];
1508 }
1509 }
1510}
int Prune(unsigned int min_nr_samples, unsigned int max_nr_samples)
Definition i_ground.cc:67

◆ ResetParams()

void apollo::perception::algorithm::PlaneFitGroundDetector::ResetParams ( float  ori_z_lower,
float  ori_z_upper 
)

在文件 i_ground.cc 第 1582 行定义.

1582 {
1583 param_.sample_region_z_lower = ori_z_lower;
1584 param_.sample_region_z_upper = ori_z_upper;
1585 AINFO << "[BEFORE]: {} " << param_.sample_region_z_lower << ",{} "
1587}

◆ SetGroundPlaneSpherParams()

void apollo::perception::algorithm::PlaneFitGroundDetector::SetGroundPlaneSpherParams ( float *  params)
protected

在文件 i_ground.cc 第 1368 行定义.

1368 {
1369 unsigned int lap_size = param_.nr_grids_coarse * param_.nr_grids_coarse;
1370 unsigned int offset = 0;
1371 for (unsigned int i = 0; i < lap_size; ++i) {
1372 ground_planes_sphe_[0][i].theta = params[i + offset];
1373 }
1374 offset += lap_size;
1375 for (unsigned int i = 0; i < lap_size; ++i) {
1376 ground_planes_sphe_[0][i].phi = params[i + offset];
1377 }
1378 offset += lap_size;
1379 for (unsigned int i = 0; i < lap_size; ++i) {
1380 ground_planes_sphe_[0][i].d = params[i + offset];
1381 }
1382 for (unsigned int r = 0; r < param_.nr_grids_coarse; ++r) {
1383 for (unsigned int c = 0; c < param_.nr_grids_coarse; ++c) {
1384 // if ((*vg_coarse_)(r, c).Empty()) {
1385 // ground_planes_[r][c].ForceInvalid();
1386 // } else {
1387 // ground_planes_sphe_[r][c].SetNrSupport(1);
1388 // IPlaneSpherToEucli(ground_planes_sphe_[r][c],
1389 // &ground_planes_[r][c]);
1390 // }
1392 }
1393 }
1394}
void IPlaneSpherToEucli(const GroundPlaneSpherical &src, GroundPlaneLiDAR *dst)
Definition i_ground.cc:1734

◆ Smooth()

int apollo::perception::algorithm::PlaneFitGroundDetector::Smooth ( )
protected

在文件 i_ground.cc 第 1349 行定义.

1349 {
1350 int nr_grids = 0;
1351 unsigned int r = 0;
1352 unsigned int c = 0;
1353 unsigned int nm1 = param_.nr_grids_coarse - 1;
1354 assert(param_.nr_grids_coarse >= 2);
1355 nr_grids += SmoothLine(0, 0, 1);
1356 for (r = 1; r < nm1; ++r) {
1357 nr_grids += SmoothLine(r - 1, r, r + 1);
1358 }
1359 nr_grids += SmoothLine(nm1 - 1, nm1, nm1);
1360 for (r = 0; r < param_.nr_grids_coarse; ++r) {
1361 for (c = 0; c < param_.nr_grids_coarse; ++c) {
1363 }
1364 }
1365 return nr_grids;
1366}
int SmoothLine(unsigned int up, unsigned int r, unsigned int dn)
Definition i_ground.cc:1196

◆ SmoothGrid()

int apollo::perception::algorithm::PlaneFitGroundDetector::SmoothGrid ( const GroundPlaneSpherical &  g,
const GroundPlaneSpherical &  lt,
const GroundPlaneSpherical &  rt,
const GroundPlaneSpherical &  up,
const GroundPlaneSpherical &  dn,
GroundPlaneSpherical *  gp 
)
protected

在文件 i_ground.cc 第 1289 行定义.

1294 {
1295 int supports[] = {0, 0, 0, 0, 0};
1296 float weights[] = {0.f, 0.f, 0.f, 0.f, 0.f};
1297 gp->ForceInvalid();
1298 if (!g.IsValid()) {
1299 return 0;
1300 }
1301 // geometry weight:
1302 // 1
1303 // 1 4 1
1304 // 1
1305 if (lt.GetStatus()) {
1306 supports[0] = lt.GetNrSupport();
1307 }
1308 if (rt.GetStatus()) {
1309 supports[1] = rt.GetNrSupport();
1310 }
1311 if (up.GetStatus()) {
1312 supports[2] = up.GetNrSupport();
1313 }
1314 if (dn.GetStatus()) {
1315 supports[3] = dn.GetNrSupport();
1316 }
1317 supports[4] = (g.GetNrSupport() << 2);
1318 int support_sum = 0;
1319 support_sum = ISum4(supports);
1320 if (support_sum == 0) {
1321 *gp = g;
1322 return 0;
1323 }
1324 support_sum += supports[4];
1325 weights[0] =
1326 static_cast<float>(supports[0]) / static_cast<float>(support_sum);
1327 weights[1] =
1328 static_cast<float>(supports[1]) / static_cast<float>(support_sum);
1329 weights[2] =
1330 static_cast<float>(supports[2]) / static_cast<float>(support_sum);
1331 weights[3] =
1332 static_cast<float>(supports[3]) / static_cast<float>(support_sum);
1333 weights[4] =
1334 static_cast<float>(supports[4]) / static_cast<float>(support_sum);
1335 // weighted average:
1336 gp->theta = weights[0] * lt.theta + weights[1] * rt.theta +
1337 weights[2] * up.theta + weights[3] * dn.theta +
1338 weights[4] * g.theta;
1339 gp->phi = weights[0] * lt.phi + weights[1] * rt.phi + weights[2] * up.phi +
1340 weights[3] * dn.phi + weights[4] * g.phi;
1341 gp->d = weights[0] * lt.d + weights[1] * rt.d + weights[2] * up.d +
1342 weights[3] * dn.d + weights[4] * g.d;
1343 // compute weighted average - diveided by 8, round to nearest int
1344 support_sum = IMax(((support_sum + 2) >> 3), 1);
1345 gp->SetNrSupport(support_sum);
1346 return 1;
1347}

◆ SmoothInMath()

void apollo::perception::algorithm::PlaneFitGroundDetector::SmoothInMath ( )
protected

◆ SmoothInOrder()

int apollo::perception::algorithm::PlaneFitGroundDetector::SmoothInOrder ( )
protected

在文件 i_ground.cc 第 1546 行定义.

1546 {
1547 int nr_grids = 0;
1548 assert(param_.nr_grids_coarse >= 2);
1549 GroundPlaneSpherical plane;
1550 int cols = param_.nr_grids_coarse;
1551 int rows = param_.nr_grids_coarse;
1552 // from center to edge
1553 for (size_t i = 0; i < vg_coarse_->NrVoxel(); i++) {
1554 int row = order_table_[i].first;
1555 int col = order_table_[i].second;
1556 int last_col = IMax(0, col - 1);
1557 int next_col = IMin(cols - 1, col + 1);
1558 int last_row = IMax(0, row - 1);
1559 int next_row = IMin(rows - 1, row + 1);
1560 if (!ground_planes_sphe_[row][col].IsValid()) {
1561 nr_grids += CompleteGrid(ground_planes_sphe_[row][last_col],
1562 ground_planes_sphe_[row][next_col],
1563 ground_planes_sphe_[last_row][col],
1564 ground_planes_sphe_[next_row][col], &plane);
1565 } else {
1566 nr_grids += SmoothGrid(ground_planes_sphe_[row][col],
1567 ground_planes_sphe_[row][last_col],
1568 ground_planes_sphe_[row][next_col],
1569 ground_planes_sphe_[last_row][col],
1570 ground_planes_sphe_[next_row][col], &plane);
1571 }
1572 IPlaneSpherToEucli(plane, &ground_planes_[row][col]);
1573 }
1574 for (unsigned int r = 0; r < param_.nr_grids_coarse; ++r) {
1575 for (unsigned int c = 0; c < param_.nr_grids_coarse; ++c) {
1577 }
1578 }
1579 return nr_grids;
1580}
int CompleteGrid(const GroundPlaneSpherical &lt, const GroundPlaneSpherical &rt, const GroundPlaneSpherical &up, const GroundPlaneSpherical &dn, GroundPlaneSpherical *gp)
Definition i_ground.cc:1251
int SmoothGrid(const GroundPlaneSpherical &g, const GroundPlaneSpherical &lt, const GroundPlaneSpherical &rt, const GroundPlaneSpherical &up, const GroundPlaneSpherical &dn, GroundPlaneSpherical *gp)
Definition i_ground.cc:1289

◆ SmoothLine()

int apollo::perception::algorithm::PlaneFitGroundDetector::SmoothLine ( unsigned int  up,
unsigned int  r,
unsigned int  dn 
)
protected

(*_vg_coarse)(r, 0).empty()

(*_vg_coarse)(r, c).empty()

(*_vg_coarse)(r, nm1).empty()

在文件 i_ground.cc 第 1196 行定义.

1197 {
1198 int nr_grids = 0;
1199 unsigned int c = 0;
1200 unsigned int nm1 = param_.nr_grids_coarse - 1;
1201 GroundPlaneSpherical plane;
1202 assert(param_.nr_grids_coarse >= 2);
1203 assert(up < param_.nr_grids_coarse);
1204 assert(r < param_.nr_grids_coarse);
1205 assert(dn < param_.nr_grids_coarse);
1206 if ( true) {
1207 if (!ground_planes_sphe_[r][0].IsValid()) {
1208 nr_grids += CompleteGrid(
1210 ground_planes_sphe_[up][0], ground_planes_sphe_[dn][0], &plane);
1211 } else {
1212 nr_grids +=
1215 ground_planes_sphe_[dn][0], &plane);
1216 }
1217 IPlaneSpherToEucli(plane, &ground_planes_[r][0]);
1218 }
1219 for (c = 1; c < nm1; ++c) {
1220 if ( true) {
1221 if (!ground_planes_sphe_[r][c].IsValid()) {
1222 nr_grids += CompleteGrid(
1223 ground_planes_sphe_[r][c - 1], ground_planes_sphe_[r][c + 1],
1224 ground_planes_sphe_[up][c], ground_planes_sphe_[dn][c], &plane);
1225 } else {
1226 nr_grids += SmoothGrid(
1228 ground_planes_sphe_[r][c + 1], ground_planes_sphe_[up][c],
1229 ground_planes_sphe_[dn][c], &plane);
1230 }
1231 IPlaneSpherToEucli(plane, &ground_planes_[r][c]);
1232 }
1233 }
1234 if ( true) {
1235 if (!ground_planes_sphe_[r][nm1].IsValid()) {
1236 nr_grids += CompleteGrid(
1237 ground_planes_sphe_[r][nm1 - 1], ground_planes_sphe_[r][nm1],
1238 ground_planes_sphe_[up][nm1], ground_planes_sphe_[dn][nm1], &plane);
1239 } else {
1240 nr_grids += SmoothGrid(
1241 ground_planes_sphe_[r][nm1], ground_planes_sphe_[r][nm1 - 1],
1242 ground_planes_sphe_[r][nm1], ground_planes_sphe_[up][nm1],
1243 ground_planes_sphe_[dn][nm1], &plane);
1244 }
1245 IPlaneSpherToEucli(plane, &ground_planes_[r][nm1]);
1246 }
1247
1248 return nr_grids;
1249}

◆ UpdateParams()

void apollo::perception::algorithm::PlaneFitGroundDetector::UpdateParams ( float  parsing_ground_z,
float  buffer,
double  timestamp 
)

在文件 i_ground.cc 第 1589 行定义.

1589 {
1591 parsing_ground_z - buffer);
1593 parsing_ground_z + buffer);
1595 AINFO << "[AFTER]: {} " << param_.sample_region_z_lower << ",{} "
1597}

类成员变量说明

◆ a_array_

Eigen::SparseMatrix<float> apollo::perception::algorithm::PlaneFitGroundDetector::a_array_
protected

在文件 i_ground.h 第 368 行定义.

◆ age_

int apollo::perception::algorithm::PlaneFitGroundDetector::age_ = 0
protected

在文件 i_ground.h 第 359 行定义.

◆ b_array_

Eigen::SparseMatrix<float> apollo::perception::algorithm::PlaneFitGroundDetector::b_array_
protected

在文件 i_ground.h 第 369 行定义.

◆ frame_timestamp_

double apollo::perception::algorithm::PlaneFitGroundDetector::frame_timestamp_ = 0.0
protected

在文件 i_ground.h 第 361 行定义.

◆ ground_planes_

GroundPlaneLiDAR** apollo::perception::algorithm::PlaneFitGroundDetector::ground_planes_
protected

在文件 i_ground.h 第 348 行定义.

◆ ground_planes_sphe_

GroundPlaneSpherical** apollo::perception::algorithm::PlaneFitGroundDetector::ground_planes_sphe_
protected

在文件 i_ground.h 第 349 行定义.

◆ ground_z_

std::pair<float, bool>** apollo::perception::algorithm::PlaneFitGroundDetector::ground_z_
protected

在文件 i_ground.h 第 351 行定义.

◆ inliers_

int* apollo::perception::algorithm::PlaneFitGroundDetector::inliers_ = nullptr
protected

在文件 i_ground.h 第 365 行定义.

◆ labels_

char* apollo::perception::algorithm::PlaneFitGroundDetector::labels_
protected

在文件 i_ground.h 第 354 行定义.

◆ local_candis_

PlaneFitPointCandIndices** apollo::perception::algorithm::PlaneFitGroundDetector::local_candis_
protected

在文件 i_ground.h 第 350 行定义.

◆ map_fine_to_coarse_

unsigned int* apollo::perception::algorithm::PlaneFitGroundDetector::map_fine_to_coarse_
protected

在文件 i_ground.h 第 353 行定义.

◆ neighbors_

std::vector<std::vector<unsigned int> > apollo::perception::algorithm::PlaneFitGroundDetector::neighbors_
protected

在文件 i_ground.h 第 367 行定义.

◆ order_table_

std::pair<int, int>* apollo::perception::algorithm::PlaneFitGroundDetector::order_table_
protected

在文件 i_ground.h 第 360 行定义.

◆ pf_threeds_

float* apollo::perception::algorithm::PlaneFitGroundDetector::pf_threeds_
protected

在文件 i_ground.h 第 356 行定义.

◆ pf_thresholds_

float** apollo::perception::algorithm::PlaneFitGroundDetector::pf_thresholds_
protected

在文件 i_ground.h 第 352 行定义.

◆ sampled_indices_

int* apollo::perception::algorithm::PlaneFitGroundDetector::sampled_indices_
protected

在文件 i_ground.h 第 358 行定义.

◆ sampled_z_values_

float* apollo::perception::algorithm::PlaneFitGroundDetector::sampled_z_values_
protected

在文件 i_ground.h 第 355 行定义.

◆ solver_

Eigen::SimplicialLDLT<Eigen::SparseMatrix<float> > apollo::perception::algorithm::PlaneFitGroundDetector::solver_
protected

在文件 i_ground.h 第 370 行定义.

◆ sphe_params_

float* apollo::perception::algorithm::PlaneFitGroundDetector::sphe_params_ = nullptr
protected

在文件 i_ground.h 第 366 行定义.

◆ spher_params_

float* apollo::perception::algorithm::PlaneFitGroundDetector::spher_params_
protected

在文件 i_ground.h 第 357 行定义.

◆ vg_coarse_

VoxelGridXY<float>* apollo::perception::algorithm::PlaneFitGroundDetector::vg_coarse_
protected

在文件 i_ground.h 第 347 行定义.

◆ vg_fine_

VoxelGridXY<float>* apollo::perception::algorithm::PlaneFitGroundDetector::vg_fine_
protected

在文件 i_ground.h 第 346 行定义.

◆ weight_buffer_

float** apollo::perception::algorithm::PlaneFitGroundDetector::weight_buffer_ = nullptr
protected

在文件 i_ground.h 第 364 行定义.


该类的文档由以下文件生成: