This is the official code repository of "Contour Context: Abstract Structural Distribution for 3D LiDAR Loop Detection and Metric Pose Estimation", which is accepted by ICRA'23.
Contour Context is a simple, effective, and efficient 3D LiDAR topological loop closure detector with accurate 3-DoF metric pose estimation, targeting the urban autonomous driving scenario. Our key insight is that the scene expressed in BEV can be modeled as a probability distribution of salient structures. A two-step discrete constellation consensus verification and GMM L2 optimization with continuous densities is used to calculate similarity between two scans, after preselecting loop candidates using an efficient retrieval key. Our method is competitive compared with many recent works on different datasets.
Authors: Binqian Jiang and Shaojie Shen from the HKUST Aerial Robotics Group.
If you find this work useful, please consider citing our paper:
@inproceedings{jiang2023contour,
address = {London, United Kingdom},
title = {Contour Context: Abstract Structural Distribution for 3D LiDAR Loop Detection and Metric Pose Estimation},
ISBN = {9798350323658},
DOI = {10.1109/ICRA48891.2023.10160337},
booktitle = {2023 IEEE International Conference on Robotics and Automation (ICRA)},
author = {Jiang, Binqian and Shen, Shaojie},
year = {2023},
pages = {8386–8392}
}
We've tested on Ubuntu 20.04 with ROS 1. The cont2contops
library, which contains all the required functions of Contour Context, is totally ROS-free.
Our project also relies on nanoflann. Note that their code has already been included in the ./thirdparty
folder after some modifications.
Official site. Note that we use GT poses from Semantic KITTI.
- Download and unzip the dataset. Put the poses files in place as Semantic KITTI.
- Download and compile code:
cd /path/to/catkin_ws/src
git clone https://github.com/lewisjiang/contour-context.git
cd .. && catkin build cont2 && source devel/setup.bash
- (Once for a sequence) In
./scripts/gen_batch_bin_configs.py
,- Uncomment a sequence and modify the path parameters in
== KITTI Odometry ==
section (== Mulran Odometry ==
for MulRan) following the commented examples. - Uncomment
gen_kitti(dir_lid_bin, fp_pose, fp_times, fp_calib, sav_1, sav_2)
(gen_mulran(...)
for MulRan) and run the script.
- Uncomment a sequence and modify the path parameters in
- In
./config/batch_bin_test_config.yaml
,- Set the
fpath_sens_gt_pose
andfpath_lidar_bins
parameters assav_1
andsav_2
respectively. - Set the
fpath_outcome_sav
in the file as you like. - (For MulRan) Modify the settings
ta_h_bar
,lv_grads_
in as instructed in the config file.
- Set the
rosrun cont2 cont2_batch_bin_test
- Terminate the program and you will find the runtime log in
./log
and topological loop detection and mpe results in./results/outcome_txt
. - Modify the file paths for gt sensor poses and outcome in
./scripts/pr_mpe.py
before running the script to get pr curve, max f1 score and metric pose estimation of a given sequence.- (For MulRan) Finish the additional steps first.
Similar to above.
Our system uses time gap to exclude past poses from the query candidates, so it may be problematic since the vehicle always stops at red lights in MulRan. Therefore we reindex the frames in MulRan to skip stationary times. To do this,
-
Finish the above 1-6.
-
In
./include/cont2/evaluator.h
,- Uncomment
// save gt pose and bin path
section and recompile. rosrun cont2 cont2_batch_bin_test
once to generate newts-sens_pose-
(for configfpath_sens_gt_pose
) andts-lidar_bins
(for configfpath_lidar_bins
) files.- Save the two new files and use them in the configuration yaml.
- Comment
// save gt pose and bin path
section and recompile.
- Uncomment
-
Run normally.
Make sure the PUB_ROS_MSG
flag is set to 1
in the cmakelists file.
cd /path/to/catkin_ws
rviz -d ./src/contour-context/config/dummy_lc.rviz & rosrun cont2 cont2_batch_bin_test
Sample image (KITTI08 at max f1 score):
Set SAVE_MID_FILE
to 1
in the cmakelists to save raw contours as images on the go.
Sample raw contours (KITTI 08, #0237 and #1648):
In ./scripts/plot_contours.py
, ...
Sample CAs from a pair of loop closure scans (transform applied, KITTI 08, #0237 and #1648):