Formula Student Autonomous Systems
The code for the main driverless system
Loading...
Searching...
No Matches
jcbb.cpp
Go to the documentation of this file.
2
3Eigen::VectorXi JCBB::associate(const Eigen::VectorXd& landmarks,
4 const Eigen::VectorXd& observations,
5 const Eigen::MatrixXd& covariance,
6 const Eigen::VectorXd& observation_confidences) const {
7 const int num_observations = observations.size() / 2;
8 const int num_landmarks = landmarks.size() / 2;
9
10 Eigen::VectorXi best_hypothesis =
11 Eigen::VectorXi::Constant(num_observations, -1); // -1 means new observation
12 Eigen::VectorXi current_hypothesis = Eigen::VectorXi::Constant(num_observations, -1);
13
14 double best_score = -1.0;
15
16 // Precompute all Euclidean distances between observations and landmarks
17 Eigen::MatrixXd distances(num_observations, num_landmarks);
18 for (int obs_idx = 0; obs_idx < num_observations; ++obs_idx) {
19 Eigen::Vector2d observation(observations(2 * obs_idx), observations(2 * obs_idx + 1));
20 for (int lm_idx = 0; lm_idx < num_landmarks; ++lm_idx) {
21 Eigen::Vector2d landmark(landmarks(2 * lm_idx), landmarks(2 * lm_idx + 1));
22 distances(obs_idx, lm_idx) = (observation - landmark).norm();
23 }
24 }
25
26 // Start the recursive branch & bound search
27 search_branch_and_bound(0, num_observations, num_landmarks, distances, current_hypothesis,
28 best_hypothesis, best_score, 0.0);
29
30 return best_hypothesis;
31}
32
33void JCBB::search_branch_and_bound(int current_obs_idx, int num_observations, int num_landmarks,
34 const Eigen::MatrixXd& distances,
35 Eigen::VectorXi& current_hypothesis,
36 Eigen::VectorXi& best_hypothesis, double& best_score,
37 double current_score) const {
38 if (current_obs_idx >= num_observations) {
39 if (current_score > best_score) {
40 best_hypothesis = current_hypothesis;
41 best_score = current_score;
42 }
43 return;
44 }
45
46 // Try pairing current observation with each landmark
47 for (int landmark_idx = 0; landmark_idx < num_landmarks; ++landmark_idx) {
48 if (distances(current_obs_idx, landmark_idx) <= this->_params_.association_gate &&
49 !is_landmark_already_assigned(current_hypothesis, landmark_idx)) {
50 current_hypothesis(current_obs_idx) = 2 * landmark_idx;
51
52 double updated_score = current_score + (this->_params_.association_gate -
53 distances(current_obs_idx, landmark_idx));
54
55 // Upper bound estimate: assume all remaining observations are perfect
56 double upper_bound = updated_score + (num_observations - current_obs_idx - 1) *
58
59 if (upper_bound >= best_score) {
60 search_branch_and_bound(current_obs_idx + 1, num_observations, num_landmarks, distances,
61 current_hypothesis, best_hypothesis, best_score, updated_score);
62 }
63
64 // backtrack
65 current_hypothesis(current_obs_idx) = -1;
66 }
67 }
68
69 // Or leave the current observation unpaired (new or clutter)
70 current_hypothesis(current_obs_idx) = -1;
71
72 double upper_bound =
73 current_score + (num_observations - current_obs_idx - 1) * this->_params_.association_gate;
74
75 if (upper_bound >= best_score) {
76 search_branch_and_bound(current_obs_idx + 1, num_observations, num_landmarks, distances,
77 current_hypothesis, best_hypothesis, best_score, current_score);
78 }
79
80 // backtrack (redundant, but clear)
81 current_hypothesis(current_obs_idx) = -1;
82}
83
84bool JCBB::is_landmark_already_assigned(const Eigen::VectorXi& hypothesis, int landmark_idx) const {
85 for (int i = 0; i < hypothesis.size(); ++i) {
86 if (hypothesis(i) == landmark_idx) return true;
87 }
88 return false;
89}
DataAssociationParameters _params_
bool is_landmark_already_assigned(const Eigen::VectorXi &hypothesis, int landmark_idx) const
Check if a landmark is already assigned in the current hypothesis.
Definition jcbb.cpp:84
Eigen::VectorXi associate(const Eigen::VectorXd &landmarks, const Eigen::VectorXd &observations, const Eigen::MatrixXd &covariance, const Eigen::VectorXd &observation_confidences) const override
Perform data association using the Joint Compatibility Branch & Bound algorithm.
Definition jcbb.cpp:3
void search_branch_and_bound(int current_obs_idx, int num_observations, int num_landmarks, const Eigen::MatrixXd &distances, Eigen::VectorXi &current_hypothesis, Eigen::VectorXi &best_hypothesis, double &best_score, double current_score) const
Recursive branch and bound search to find the best hypothesis.
Definition jcbb.cpp:33