删除文件夹
This commit is contained in:
		
							parent
							
								
									aed223518c
								
							
						
					
					
						commit
						836d4112e4
					
				
							
								
								
									
										47
									
								
								SLAM/.gitignore
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										47
									
								
								SLAM/.gitignore
									
									
									
									
										vendored
									
									
								
							| @ -1,47 +0,0 @@ | ||||
| .vscode | ||||
| 
 | ||||
| CMakeLists.txt.user | ||||
| CMakeLists_modified.txt | ||||
| 
 | ||||
| Examples/RGB-D/rgbd_tum | ||||
| 
 | ||||
| Examples/Monocular/mono_euroc | ||||
| Examples/Monocular/mono_kitti | ||||
| Examples/Monocular/mono_tum | ||||
| Examples/Monocular/mono_tum_vi | ||||
| 
 | ||||
| Examples/Stereo/stereo_euroc | ||||
| Examples/Stereo/stereo_kitti | ||||
| Examples/Stereo/stereo_tum_vi | ||||
| 
 | ||||
| Examples/Monocular-Inertial/mono_inertial_euroc | ||||
| Examples/Monocular-Inertial/mono_inertial_tum_vi | ||||
| 
 | ||||
| Examples/Stereo-Inertial/stereo_inertial_euroc | ||||
| Examples/Stereo-Inertial/stereo_inertial_tum_vi | ||||
| 
 | ||||
| Examples/ROS/ORB_SLAM3/Mono | ||||
| Examples/ROS/ORB_SLAM3/MonoAR | ||||
| Examples/ROS/ORB_SLAM3/RGBD | ||||
| Examples/ROS/ORB_SLAM3/Stereo | ||||
| 
 | ||||
| Examples/ROS/ORB_SLAM3/CMakeLists.txt.user | ||||
| Examples/ROS/ORB_SLAM3/build/ | ||||
| 
 | ||||
| KeyFrameTrajectory.txt | ||||
| CameraTrajectory.txt | ||||
| kf_*.txt | ||||
| f_*.txt | ||||
| Thirdparty/DBoW2/build/ | ||||
| Thirdparty/DBoW2/lib/ | ||||
| Thirdparty/g2o/build/ | ||||
| Thirdparty/g2o/config.h | ||||
| Thirdparty/g2o/lib/ | ||||
| Vocabulary/ORBvoc.txt | ||||
| build/ | ||||
| 
 | ||||
| lib/ | ||||
| 
 | ||||
| cmake-build-debug/ | ||||
| 
 | ||||
| *.pyc | ||||
| @ -1,296 +0,0 @@ | ||||
| cmake_minimum_required(VERSION 2.8.3) | ||||
| project(rds_slam) | ||||
| 
 | ||||
| # enable this if you want to debug using gdb | ||||
| # SET(CMAKE_BUILD_TYPE Debug) | ||||
| 
 | ||||
| # IF(NOT CMAKE_BUILD_TYPE) | ||||
| #   SET(CMAKE_BUILD_TYPE Release) | ||||
| # ENDIF() | ||||
| SET(CMAKE_BUILD_TYPE Release) | ||||
| 
 | ||||
| ## Compile as C++11, supported in ROS Kinetic and newer | ||||
| add_compile_options(-std=c++11) | ||||
| 
 | ||||
| set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS}  -Wall  -O3 -march=native ") | ||||
| set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall  -O3 -march=native") | ||||
| 
 | ||||
| # set optimization level to -O1  if you want to debug using gdb | ||||
| # set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS}  -Wall  -O1 -march=native ") | ||||
| # set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall  -O1 -march=native") | ||||
| 
 | ||||
| 
 | ||||
| # Check C++11 or C++0x support | ||||
| include(CheckCXXCompilerFlag) | ||||
| CHECK_CXX_COMPILER_FLAG("-std=c++11" COMPILER_SUPPORTS_CXX11) | ||||
| CHECK_CXX_COMPILER_FLAG("-std=c++0x" COMPILER_SUPPORTS_CXX0X) | ||||
| if(COMPILER_SUPPORTS_CXX11) | ||||
|    set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11") | ||||
|    add_definitions(-DCOMPILEDWITHC11) | ||||
|    message(STATUS "Using flag -std=c++11.") | ||||
| elseif(COMPILER_SUPPORTS_CXX0X) | ||||
|    set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++0x") | ||||
|    add_definitions(-DCOMPILEDWITHC0X) | ||||
|    message(STATUS "Using flag -std=c++0x.") | ||||
| else() | ||||
|    message(FATAL_ERROR "The compiler ${CMAKE_CXX_COMPILER} has no C++11 support. Please use a different C++ compiler.") | ||||
| endif() | ||||
| 
 | ||||
| 
 | ||||
| LIST(APPEND CMAKE_MODULE_PATH ${PROJECT_SOURCE_DIR}/cmake_modules) | ||||
| 
 | ||||
| ## Find catkin macros and libraries | ||||
| ## if COMPONENTS list like find_package(catkin REQUIRED COMPONENTS xyz) | ||||
| ## is used, also find other catkin packages | ||||
| find_package(catkin REQUIRED COMPONENTS | ||||
| roscpp | ||||
| rospy | ||||
| std_msgs | ||||
| cv_bridge | ||||
| image_transport | ||||
| tf | ||||
| sensor_msgs | ||||
| dynamic_reconfigure | ||||
| message_generation | ||||
| maskrcnn_ros | ||||
| segnet_ros | ||||
| ultralytics_ros | ||||
| ) | ||||
| 
 | ||||
| ## System dependencies are found with CMake's conventions | ||||
| find_package(Boost REQUIRED COMPONENTS system) | ||||
| 
 | ||||
| find_package(OpenCV 3.3.1) | ||||
| find_package(Eigen3 3.1.0 REQUIRED) | ||||
| find_package(Pangolin REQUIRED) | ||||
| find_package(Glog REQUIRED) | ||||
| 
 | ||||
| ## Uncomment this if the package has a setup.py. This macro ensures | ||||
| ## modules and global scripts declared therein get installed | ||||
| ## See http://ros.org/doc/api/catkin/html/user_guide/setup_dot_py.html | ||||
| # catkin_python_setup() | ||||
| 
 | ||||
| ################################################ | ||||
| ## Declare ROS messages, services and actions ## | ||||
| ################################################ | ||||
| 
 | ||||
| ## To declare and build messages, services or actions from within this | ||||
| ## package, follow these steps: | ||||
| ## * Let MSG_DEP_SET be the set of packages whose message types you use in | ||||
| ##   your messages/services/actions (e.g. std_msgs, actionlib_msgs, ...). | ||||
| ## * In the file package.xml: | ||||
| ##   * add a build_depend tag for "message_generation" | ||||
| ##   * add a build_depend and a exec_depend tag for each package in MSG_DEP_SET | ||||
| ##   * If MSG_DEP_SET isn't empty the following dependency has been pulled in | ||||
| ##     but can be declared for certainty nonetheless: | ||||
| ##     * add a exec_depend tag for "message_runtime" | ||||
| ## * In this file (CMakeLists.txt): | ||||
| ##   * add "message_generation" and every package in MSG_DEP_SET to | ||||
| ##     find_package(catkin REQUIRED COMPONENTS ...) | ||||
| ##   * add "message_runtime" and every package in MSG_DEP_SET to | ||||
| ##     catkin_package(CATKIN_DEPENDS ...) | ||||
| ##   * uncomment the add_*_files sections below as needed | ||||
| ##     and list every .msg/.srv/.action file to be processed | ||||
| ##   * uncomment the generate_messages entry below | ||||
| ##   * add every package in MSG_DEP_SET to generate_messages(DEPENDENCIES ...) | ||||
| 
 | ||||
| ## Generate messages in the 'msg' folder | ||||
| # add_message_files( | ||||
| #   FILES | ||||
| #   Message1.msg | ||||
| #   Message2.msg | ||||
| # ) | ||||
| 
 | ||||
| ## Generate services in the 'srv' folder | ||||
| # add_service_files( | ||||
| #   FILES | ||||
| #   Service1.srv | ||||
| #   Service2.srv | ||||
| # ) | ||||
| 
 | ||||
| ## Generate actions in the 'action' folder | ||||
| # add_action_files( | ||||
| #   FILES | ||||
| #   Action1.action | ||||
| #   Action2.action | ||||
| # ) | ||||
| 
 | ||||
| ## Generate added messages and services with any dependencies listed here | ||||
| # generate_messages( | ||||
| #   DEPENDENCIES | ||||
| #   std_msgs  # Or other packages containing msgs | ||||
| # ) | ||||
| 
 | ||||
| ################################################ | ||||
| ## Declare ROS dynamic reconfigure parameters ## | ||||
| ################################################ | ||||
| 
 | ||||
| ## To declare and build dynamic reconfigure parameters within this | ||||
| ## package, follow these steps: | ||||
| ## * In the file package.xml: | ||||
| ##   * add a build_depend and a exec_depend tag for "dynamic_reconfigure" | ||||
| ## * In this file (CMakeLists.txt): | ||||
| ##   * add "dynamic_reconfigure" to | ||||
| ##     find_package(catkin REQUIRED COMPONENTS ...) | ||||
| ##   * uncomment the "generate_dynamic_reconfigure_options" section below | ||||
| ##     and list every .cfg file to be processed | ||||
| 
 | ||||
| ## Generate dynamic reconfigure parameters in the 'cfg' folder | ||||
| # generate_dynamic_reconfigure_options( | ||||
| #   cfg/DynReconf1.cfg | ||||
| #   cfg/DynReconf2.cfg | ||||
| # ) | ||||
| 
 | ||||
| ################################### | ||||
| ## catkin specific configuration ## | ||||
| ################################### | ||||
| ## The catkin_package macro generates cmake config files for your package | ||||
| ## Declare things to be passed to dependent projects | ||||
| ## INCLUDE_DIRS: uncomment this if your package contains header files | ||||
| ## LIBRARIES: libraries you create in this project that dependent projects also need | ||||
| ## CATKIN_DEPENDS: catkin_packages dependent projects also need | ||||
| ## DEPENDS: system dependencies of this project that dependent projects also need | ||||
| catkin_package( | ||||
|  INCLUDE_DIRS include | ||||
|  LIBRARIES rds_slam | ||||
|  CATKIN_DEPENDS roscpp rospy std_msgs cv_bridge image_transport tf sensor_msgs dynamic_reconfigure message_generation  segnet_ros maskrcnn_ros ultralytics_ros | ||||
| #  DEPENDS system_lib | ||||
| ) | ||||
| 
 | ||||
| ########### | ||||
| ## Build ## | ||||
| ########### | ||||
| 
 | ||||
| ## Specify additional locations of header files | ||||
| ## Your package locations should be listed before other locations | ||||
| # message("Project Source Directory: ${PROJECT_SOURCE_DIR}") | ||||
| # message("${catkin_INCLUDE_DIRS}: ${catkin_INCLUDE_DIRS}") | ||||
| 
 | ||||
| include_directories( | ||||
|     include | ||||
|     ${catkin_INCLUDE_DIRS} | ||||
|     ${PROJECT_SOURCE_DIR} | ||||
|     ${PROJECT_SOURCE_DIR}/include | ||||
|     ${PROJECT_SOURCE_DIR}/include/CameraModels | ||||
|     ${EIGEN3_INCLUDE_DIR} | ||||
|     ${Pangolin_INCLUDE_DIRS} | ||||
|     ${Boost_INCLUDE_DIRS} | ||||
|     ${GLOG_INCLUDE_DIR} | ||||
|     # TODO not use absolute path | ||||
|     /root/catkin_ws/devel/include | ||||
| ) | ||||
| 
 | ||||
| aux_source_directory(src DIR_LIB_SRCS) | ||||
| 
 | ||||
| add_subdirectory(Thirdparty/g2o) | ||||
| add_subdirectory(Thirdparty/DBoW2) | ||||
| 
 | ||||
| # Declare a C++ library | ||||
| add_library(${PROJECT_NAME} | ||||
|     ${DIR_LIB_SRCS} | ||||
|     src/CameraModels/Pinhole.cpp | ||||
|     src/CameraModels/KannalaBrandt8.cpp | ||||
|     include/CameraModels/GeometricCamera.h | ||||
|     include/CameraModels/Pinhole.h | ||||
|     include/CameraModels/KannalaBrandt8.h | ||||
| ) | ||||
| 
 | ||||
| target_link_libraries(${PROJECT_NAME} | ||||
| ${OpenCV_LIBS} | ||||
| ${EIGEN3_LIBS} | ||||
| ${Pangolin_LIBRARIES} | ||||
| ${PROJECT_SOURCE_DIR}/Thirdparty/DBoW2/lib/libDBoW2.so | ||||
| ${PROJECT_SOURCE_DIR}/Thirdparty/g2o/lib/libg2o.so | ||||
| ${catkin_LIBRARIES} | ||||
| ${Boost_LIBRARIES} | ||||
| ${GLOG_LIBRARY} | ||||
| -lboost_serialization | ||||
| -lcrypto | ||||
| # aislamwrapper | ||||
| ) | ||||
| 
 | ||||
| add_executable(Dynamic_RGBD Examples/ros_tum_rgbd.cpp) | ||||
| add_dependencies(Dynamic_RGBD ${${PROJECT_NAME}_EXPORTED_TARGETS} ${catkin_EXPORTED_TARGETS}) | ||||
| target_link_libraries(Dynamic_RGBD | ||||
|     ${PROJECT_NAME} | ||||
| ) | ||||
| 
 | ||||
| ## Add cmake target dependencies of the library | ||||
| ## as an example, code may need to be generated before libraries | ||||
| ## either from message generation or dynamic reconfigure | ||||
| # add_dependencies(${PROJECT_NAME} ${${PROJECT_NAME}_EXPORTED_TARGETS} ${catkin_EXPORTED_TARGETS}) | ||||
| 
 | ||||
| ## Declare a C++ executable | ||||
| ## With catkin_make all packages are built within a single CMake context | ||||
| ## The recommended prefix ensures that target names across packages don't collide | ||||
| # add_executable(${PROJECT_NAME}_node src/orbslam_ros_node.cpp) | ||||
| 
 | ||||
| ## Rename C++ executable without prefix | ||||
| ## The above recommended prefix causes long target names, the following renames the | ||||
| ## target back to the shorter version for ease of user use | ||||
| ## e.g. "rosrun someones_pkg node" instead of "rosrun someones_pkg someones_pkg_node" | ||||
| # set_target_properties(${PROJECT_NAME}_node PROPERTIES OUTPUT_NAME node PREFIX "") | ||||
| 
 | ||||
| ## Add cmake target dependencies of the executable | ||||
| ## same as for the library above | ||||
| # add_dependencies(${PROJECT_NAME}_node ${${PROJECT_NAME}_EXPORTED_TARGETS} ${catkin_EXPORTED_TARGETS}) | ||||
| 
 | ||||
| ## Specify libraries to link a library or executable target against | ||||
| # target_link_libraries(${PROJECT_NAME}_node | ||||
| #   ${catkin_LIBRARIES} | ||||
| # ) | ||||
| 
 | ||||
| ############# | ||||
| ## Install ## | ||||
| ############# | ||||
| 
 | ||||
| # all install targets should use catkin DESTINATION variables | ||||
| # See http://ros.org/doc/api/catkin/html/adv_user_guide/variables.html | ||||
| 
 | ||||
| ## Mark executable scripts (Python etc.) for installation | ||||
| ## in contrast to setup.py, you can choose the destination | ||||
| # install(PROGRAMS | ||||
| #   scripts/my_python_script | ||||
| #   DESTINATION ${CATKIN_PACKAGE_BIN_DESTINATION} | ||||
| # ) | ||||
| 
 | ||||
| ## Mark executables for installation | ||||
| ## See http://docs.ros.org/melodic/api/catkin/html/howto/format1/building_executables.html | ||||
| # install(TARGETS ${PROJECT_NAME}_node | ||||
| #   RUNTIME DESTINATION ${CATKIN_PACKAGE_BIN_DESTINATION} | ||||
| # ) | ||||
| 
 | ||||
| ## Mark libraries for installation | ||||
| ## See http://docs.ros.org/melodic/api/catkin/html/howto/format1/building_libraries.html | ||||
| # install(TARGETS ${PROJECT_NAME} | ||||
| #   ARCHIVE DESTINATION ${CATKIN_PACKAGE_LIB_DESTINATION} | ||||
| #   LIBRARY DESTINATION ${CATKIN_PACKAGE_LIB_DESTINATION} | ||||
| #   RUNTIME DESTINATION ${CATKIN_GLOBAL_BIN_DESTINATION} | ||||
| # ) | ||||
| 
 | ||||
| ## Mark cpp header files for installation | ||||
| # install(DIRECTORY include/${PROJECT_NAME}/ | ||||
| #   DESTINATION ${CATKIN_PACKAGE_INCLUDE_DESTINATION} | ||||
| #   FILES_MATCHING PATTERN "*.h" | ||||
| #   PATTERN ".svn" EXCLUDE | ||||
| # ) | ||||
| 
 | ||||
| ## Mark other files for installation (e.g. launch and bag files, etc.) | ||||
| # install(FILES | ||||
| #   # myfile1 | ||||
| #   # myfile2 | ||||
| #   DESTINATION ${CATKIN_PACKAGE_SHARE_DESTINATION} | ||||
| # ) | ||||
| 
 | ||||
| ############# | ||||
| ## Testing ## | ||||
| ############# | ||||
| 
 | ||||
| ## Add gtest based cpp test target and link libraries | ||||
| # catkin_add_gtest(${PROJECT_NAME}-test test/test_orbslam_ros.cpp) | ||||
| # if(TARGET ${PROJECT_NAME}-test) | ||||
| #   target_link_libraries(${PROJECT_NAME}-test ${PROJECT_NAME}) | ||||
| # endif() | ||||
| 
 | ||||
| ## Add folders to be run by python nosetests | ||||
| # catkin_add_nosetests(test) | ||||
| @ -1,197 +0,0 @@ | ||||
| /* 
 | ||||
|  * Copyright (C) 2021, Yubao Liu, AISL, TOYOHASHI UNIVERSITY of TECHNOLOGY  | ||||
|  * Email: yubao.liu.ra@tut.jp  | ||||
|  *  | ||||
|  */ | ||||
| 
 | ||||
| #include "Semantic.h" | ||||
| #include "System.h" | ||||
| #include <algorithm> | ||||
| #include <chrono> | ||||
| #include <fstream> | ||||
| #include <iostream> | ||||
| #include <opencv2/core/core.hpp> | ||||
| #include <ros/ros.h> | ||||
| 
 | ||||
| using namespace std; | ||||
| using namespace ORB_SLAM3; | ||||
| 
 | ||||
| void spin_thread() | ||||
| { | ||||
|     ros::spinOnce(); | ||||
|     usleep(1); | ||||
| } | ||||
| 
 | ||||
| int main(int argc, char** argv) | ||||
| { | ||||
|     google::InitGoogleLogging(argv[0]); | ||||
|     ros::init(argc, argv, "tum_rgbd_raw"); | ||||
|     ros::start(); | ||||
|     ros::NodeHandle nh("~"); | ||||
| 
 | ||||
|     if (argc < 5) { | ||||
|         cerr << endl | ||||
|              << "Usage: EXE ./Dynamic_RGBD path_to_vocabulary path_to_settings path_to_sequence path_to_association" << endl; | ||||
|         ros::shutdown(); | ||||
|         return 1; | ||||
|     } | ||||
| 
 | ||||
|     std::string rgb_image_topic, depth_image_topic, bagfile_name; | ||||
| 
 | ||||
|     std::cout << "===========================" << std::endl; | ||||
|     std::cout << "argv[1]: " << argv[1] << std::endl; | ||||
|     std::cout << "argv[2]: " << argv[2] << std::endl; | ||||
|     std::cout << "argv[3]: " << argv[3] << std::endl; | ||||
|     std::cout << "argv[4]: " << argv[4] << std::endl; | ||||
|     std::cout << "argv[5] result path: " << argv[5] << std::endl; | ||||
| 
 | ||||
|     LOG(INFO) << "---------Parameters---------------"; | ||||
|     LOG(INFO) << "argv[1]: " << argv[1]; | ||||
|     LOG(INFO) << "argv[2]: " << argv[2]; | ||||
|     LOG(INFO) << "argv[3]: " << argv[3]; | ||||
|     LOG(INFO) << "argv[4]: " << argv[4]; | ||||
|     LOG(INFO) << "argv[5] result path: " << argv[5]; | ||||
|     LOG(INFO) << "----------------------------------"; | ||||
|     std::cout << "===========================" << std::endl; | ||||
| 
 | ||||
|     // save result
 | ||||
|     if (argc == 6) { | ||||
|         Config::GetInstance()->IsSaveResult(true); | ||||
|         Config::GetInstance()->createSavePath(std::string(argv[5])); | ||||
|     } else { | ||||
|         Config::GetInstance()->IsSaveResult(false); | ||||
|     } | ||||
| 
 | ||||
|     std::thread(spin_thread); | ||||
| 
 | ||||
|     // Retrieve paths to images
 | ||||
|     std::vector<std::string> vstrImageFilenamesRGB; | ||||
|     std::vector<std::string> vstrImageFilenamesD; | ||||
|     std::vector<double> vTimestamps; | ||||
|     std::string strAssociationFilename = std::string(argv[4]); | ||||
| 
 | ||||
|     Config::GetInstance()->LoadTUMDataset(strAssociationFilename, vstrImageFilenamesRGB, vstrImageFilenamesD, vTimestamps); | ||||
| 
 | ||||
|     // Check consistency in the number of images and depthmaps
 | ||||
|     int nImages = vstrImageFilenamesRGB.size(); | ||||
|     if (vstrImageFilenamesRGB.empty()) { | ||||
|         cerr << endl | ||||
|              << "No images found in provided path." << endl; | ||||
|         return 1; | ||||
|     } else if (vstrImageFilenamesD.size() != vstrImageFilenamesRGB.size()) { | ||||
|         cerr << endl | ||||
|              << "Different number of images for rgb and depth." << endl; | ||||
|         return 1; | ||||
|     } | ||||
| 
 | ||||
|     std::string cnn_method = "yolov8"; // myx maskrcnn segnet
 | ||||
|     // SegNet case do not need set the "init_delay" and "frame_delay"
 | ||||
|     // delay for the initial few frames
 | ||||
|     float init_delay = 0.05; //usec
 | ||||
|     int init_frames = 2;    //usec
 | ||||
|     // delay for each frame
 | ||||
|     float frame_delay = 0; | ||||
| 
 | ||||
|     nh.getParam("cnn_method", cnn_method); | ||||
|     // control the framerate
 | ||||
|     nh.getParam("init_delay", init_delay); | ||||
|     nh.getParam("frame_delay", frame_delay); | ||||
|     nh.getParam("init_frames", init_frames); | ||||
| 
 | ||||
|     LOG(INFO) << "Delay for the initial few frames: " << init_delay; | ||||
| 
 | ||||
|     Semantic::GetInstance()->SetSemanticMethod(cnn_method); | ||||
| 
 | ||||
|     // Create SLAM system. It initializes all system threads and gets ready to process frames.
 | ||||
|     ORB_SLAM3::System SLAM(argv[1], argv[2], ORB_SLAM3::System::RGBD, true); | ||||
| 
 | ||||
|     Semantic::GetInstance()->Run(); | ||||
| 
 | ||||
|     std::vector<float> vTimesTrack; | ||||
|     vTimesTrack.resize(nImages); | ||||
| 
 | ||||
|     cv::Mat imRGB, imD; | ||||
|     for (int ni = 0; ni < nImages; ni++) { | ||||
|         // Read image and depthmap from file
 | ||||
|         imRGB = cv::imread(std::string(argv[3]) + "/" + vstrImageFilenamesRGB[ni], cv::IMREAD_UNCHANGED); | ||||
|         imD = cv::imread(std::string(argv[3]) + "/" + vstrImageFilenamesD[ni], cv::IMREAD_UNCHANGED); | ||||
|         double tframe = vTimestamps[ni]; | ||||
| 
 | ||||
|         if (imRGB.empty()) { | ||||
|             cerr << endl | ||||
|                  << "Failed to load image at: " | ||||
|                  << std::string(argv[3]) << "/" << vstrImageFilenamesRGB[ni] << endl; | ||||
|             return 1; | ||||
|         } | ||||
| 
 | ||||
| #ifdef COMPILEDWITHC11 | ||||
|         std::chrono::steady_clock::time_point t1 = std::chrono::steady_clock::now(); | ||||
| #else | ||||
|         std::chrono::monotonic_clock::time_point t1 = std::chrono::monotonic_clock::now(); | ||||
| #endif | ||||
| 
 | ||||
|         // Pass the image to the SLAM system
 | ||||
|         SLAM.TrackRGBD(imRGB, imD, tframe); | ||||
| 
 | ||||
|         // Manually add delay to evaluate TUM, because TUM dataset is very short
 | ||||
|         if (ni < init_frames) { | ||||
|             usleep(init_delay); | ||||
|         } else { | ||||
|             usleep(frame_delay); | ||||
|         } | ||||
| 
 | ||||
| #ifdef COMPILEDWITHC11 | ||||
|         std::chrono::steady_clock::time_point t2 = std::chrono::steady_clock::now(); | ||||
| #else | ||||
|         std::chrono::monotonic_clock::time_point t2 = std::chrono::monotonic_clock::now(); | ||||
| #endif | ||||
| 
 | ||||
|         double ttrack = std::chrono::duration_cast<std::chrono::duration<double> >(t2 - t1).count(); | ||||
| 
 | ||||
|         vTimesTrack[ni] = ttrack; | ||||
| 
 | ||||
|         // Wait to load the next frame
 | ||||
|         double T = 0; | ||||
|         if (ni < nImages - 1) | ||||
|             T = vTimestamps[ni + 1] - tframe; | ||||
|         else if (ni > 0) | ||||
|             T = tframe - vTimestamps[ni - 1]; | ||||
| 
 | ||||
|         if (ttrack < T) | ||||
|             usleep((T - ttrack) * 1e6); | ||||
|     } | ||||
| 
 | ||||
|     LOG(INFO) << "===============Tracking Finished============"; | ||||
|     std::cout << "===============Tracking Finished============" << std::endl; | ||||
| 
 | ||||
|     // ros::spin();
 | ||||
| 
 | ||||
|     LOG(INFO) << "===============Final Stage============"; | ||||
|     std::cout << "===============Final Stage============" << std::endl; | ||||
| 
 | ||||
|     // Stop semantic thread
 | ||||
|     // Semantic::GetInstance()->RequestFinish();
 | ||||
| 
 | ||||
|     // Stop all threads
 | ||||
|     SLAM.Shutdown(); | ||||
| 
 | ||||
|     // Tracking time statistics
 | ||||
|     std::sort(vTimesTrack.begin(), vTimesTrack.end()); | ||||
|     float totaltime = 0; | ||||
|     for (int ni = 0; ni < nImages; ni++) { | ||||
|         totaltime += vTimesTrack[ni]; | ||||
|     } | ||||
|     cout << "-------" << endl; | ||||
|     cout << "median tracking time: " << vTimesTrack[nImages / 2] << endl; | ||||
|     LOG(INFO) << "median tracking time: " << vTimesTrack[nImages / 2] * 1000 << "ms"; | ||||
|     cout << "mean tracking time: " << totaltime / nImages << endl; | ||||
|     LOG(INFO) << "mean tracking time: " << totaltime / nImages * 1000 << "ms"; | ||||
| 
 | ||||
|     // Save camera trajectory
 | ||||
|     SLAM.SaveTrajectoryTUM("CameraTrajectory.txt"); | ||||
|     SLAM.SaveKeyFrameTrajectoryTUM("KeyFrameTrajectory.txt"); | ||||
| 
 | ||||
|     ros::shutdown(); | ||||
| 
 | ||||
|     return 0; | ||||
| } | ||||
| @ -1,31 +0,0 @@ | ||||
| # Manually Build Probject | ||||
| 
 | ||||
| ```sh | ||||
| cd ~/catkin_ws/src/SLAM/ | ||||
| ./build_thirdparty.sh | ||||
| 
 | ||||
| cd ~/catkin_ws/src | ||||
| catkin_make | ||||
| ``` | ||||
| 
 | ||||
| # Run SLAM client | ||||
| 
 | ||||
| ## SegNet Version | ||||
| 
 | ||||
| ```sh | ||||
| roslaunch rds_slam tum_segnet_walk_xyz.launch | ||||
| ``` | ||||
| 
 | ||||
| ## MaskRCNN Version | ||||
| 
 | ||||
| ```sh | ||||
| roslaunch rds_slam tum_maskrcnn_walk_xyz.launch | ||||
| ``` | ||||
| 
 | ||||
| # How to control the framerate | ||||
| 
 | ||||
| Due to the performance is somehow related to the GPU configuration, you can trade off the tracking performance and real-time performance by adjusting these parameters. | ||||
| 
 | ||||
| -   init_delay: the delay of first few frames | ||||
| -   frame_delay: the delay of each frame other than the first few frames | ||||
| -   init_frames: wait some time for the first few frames | ||||
							
								
								
									
										40
									
								
								SLAM/Thirdparty/DBoW2/CMakeLists.txt
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										40
									
								
								SLAM/Thirdparty/DBoW2/CMakeLists.txt
									
									
									
									
										vendored
									
									
								
							| @ -1,40 +0,0 @@ | ||||
| cmake_minimum_required(VERSION 2.8) | ||||
| project(DBoW2) | ||||
| 
 | ||||
| set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS}  -Wall  -O3 -march=native ") | ||||
| set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall  -O3 -march=native") | ||||
| 
 | ||||
| set(HDRS_DBOW2 | ||||
|   DBoW2/BowVector.h | ||||
|   DBoW2/FORB.h  | ||||
|   DBoW2/FClass.h        | ||||
|   DBoW2/FeatureVector.h | ||||
|   DBoW2/ScoringObject.h    | ||||
|   DBoW2/TemplatedVocabulary.h) | ||||
| set(SRCS_DBOW2 | ||||
|   DBoW2/BowVector.cpp | ||||
|   DBoW2/FORB.cpp       | ||||
|   DBoW2/FeatureVector.cpp | ||||
|   DBoW2/ScoringObject.cpp) | ||||
| 
 | ||||
| set(HDRS_DUTILS | ||||
|   DUtils/Random.h | ||||
|   DUtils/Timestamp.h) | ||||
| set(SRCS_DUTILS | ||||
|   DUtils/Random.cpp | ||||
|   DUtils/Timestamp.cpp) | ||||
| 
 | ||||
| find_package(OpenCV 3.0 QUIET) | ||||
| if(NOT OpenCV_FOUND) | ||||
|    find_package(OpenCV 2.4.3 QUIET) | ||||
|    if(NOT OpenCV_FOUND) | ||||
|       message(FATAL_ERROR "OpenCV > 2.4.3 not found.") | ||||
|    endif() | ||||
| endif() | ||||
| 
 | ||||
| set(LIBRARY_OUTPUT_PATH ${PROJECT_SOURCE_DIR}/lib) | ||||
| 
 | ||||
| include_directories(${OpenCV_INCLUDE_DIRS}) | ||||
| add_library(DBoW2 SHARED ${SRCS_DBOW2} ${SRCS_DUTILS}) | ||||
| target_link_libraries(DBoW2 ${OpenCV_LIBS}) | ||||
| 
 | ||||
							
								
								
									
										130
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/BowVector.cpp
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										130
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/BowVector.cpp
									
									
									
									
										vendored
									
									
								
							| @ -1,130 +0,0 @@ | ||||
| /**
 | ||||
|  * File: BowVector.cpp | ||||
|  * Date: March 2011 | ||||
|  * Author: Dorian Galvez-Lopez | ||||
|  * Description: bag of words vector | ||||
|  * License: see the LICENSE.txt file | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #include <iostream> | ||||
| #include <fstream> | ||||
| #include <vector> | ||||
| #include <algorithm> | ||||
| #include <cmath> | ||||
| 
 | ||||
| #include "BowVector.h" | ||||
| 
 | ||||
| namespace DBoW2 { | ||||
| 
 | ||||
| // --------------------------------------------------------------------------
 | ||||
| 
 | ||||
| BowVector::BowVector(void) | ||||
| { | ||||
| } | ||||
| 
 | ||||
| // --------------------------------------------------------------------------
 | ||||
| 
 | ||||
| BowVector::~BowVector(void) | ||||
| { | ||||
| } | ||||
| 
 | ||||
| // --------------------------------------------------------------------------
 | ||||
| 
 | ||||
| void BowVector::addWeight(WordId id, WordValue v) | ||||
| { | ||||
|   BowVector::iterator vit = this->lower_bound(id); | ||||
|    | ||||
|   if(vit != this->end() && !(this->key_comp()(id, vit->first))) | ||||
|   { | ||||
|     vit->second += v; | ||||
|   } | ||||
|   else | ||||
|   { | ||||
|     this->insert(vit, BowVector::value_type(id, v)); | ||||
|   } | ||||
| } | ||||
| 
 | ||||
| // --------------------------------------------------------------------------
 | ||||
| 
 | ||||
| void BowVector::addIfNotExist(WordId id, WordValue v) | ||||
| { | ||||
|   BowVector::iterator vit = this->lower_bound(id); | ||||
|    | ||||
|   if(vit == this->end() || (this->key_comp()(id, vit->first))) | ||||
|   { | ||||
|     this->insert(vit, BowVector::value_type(id, v)); | ||||
|   } | ||||
| } | ||||
| 
 | ||||
| // --------------------------------------------------------------------------
 | ||||
| 
 | ||||
| void BowVector::normalize(LNorm norm_type) | ||||
| { | ||||
|   double norm = 0.0;  | ||||
|   BowVector::iterator it; | ||||
| 
 | ||||
|   if(norm_type == DBoW2::L1) | ||||
|   { | ||||
|     for(it = begin(); it != end(); ++it) | ||||
|       norm += fabs(it->second); | ||||
|   } | ||||
|   else | ||||
|   { | ||||
|     for(it = begin(); it != end(); ++it) | ||||
|       norm += it->second * it->second; | ||||
| 		norm = sqrt(norm);   | ||||
|   } | ||||
| 
 | ||||
|   if(norm > 0.0) | ||||
|   { | ||||
|     for(it = begin(); it != end(); ++it) | ||||
|       it->second /= norm; | ||||
|   } | ||||
| } | ||||
| 
 | ||||
| // --------------------------------------------------------------------------
 | ||||
| 
 | ||||
| std::ostream& operator<< (std::ostream &out, const BowVector &v) | ||||
| { | ||||
|   BowVector::const_iterator vit; | ||||
|   std::vector<unsigned int>::const_iterator iit; | ||||
|   unsigned int i = 0;  | ||||
|   const unsigned int N = v.size(); | ||||
|   for(vit = v.begin(); vit != v.end(); ++vit, ++i) | ||||
|   { | ||||
|     out << "<" << vit->first << ", " << vit->second << ">"; | ||||
|      | ||||
|     if(i < N-1) out << ", "; | ||||
|   } | ||||
|   return out; | ||||
| } | ||||
| 
 | ||||
| // --------------------------------------------------------------------------
 | ||||
| 
 | ||||
| void BowVector::saveM(const std::string &filename, size_t W) const | ||||
| { | ||||
|   std::fstream f(filename.c_str(), std::ios::out); | ||||
|    | ||||
|   WordId last = 0; | ||||
|   BowVector::const_iterator bit; | ||||
|   for(bit = this->begin(); bit != this->end(); ++bit) | ||||
|   { | ||||
|     for(; last < bit->first; ++last) | ||||
|     { | ||||
|       f << "0 "; | ||||
|     } | ||||
|     f << bit->second << " "; | ||||
|      | ||||
|     last = bit->first + 1; | ||||
|   } | ||||
|   for(; last < (WordId)W; ++last) | ||||
|     f << "0 "; | ||||
|    | ||||
|   f.close(); | ||||
| } | ||||
| 
 | ||||
| // --------------------------------------------------------------------------
 | ||||
| 
 | ||||
| } // namespace DBoW2
 | ||||
| 
 | ||||
							
								
								
									
										119
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/BowVector.h
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										119
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/BowVector.h
									
									
									
									
										vendored
									
									
								
							| @ -1,119 +0,0 @@ | ||||
| /**
 | ||||
|  * File: BowVector.h | ||||
|  * Date: March 2011 | ||||
|  * Author: Dorian Galvez-Lopez | ||||
|  * Description: bag of words vector | ||||
|  * License: see the LICENSE.txt file | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #ifndef __D_T_BOW_VECTOR__ | ||||
| #define __D_T_BOW_VECTOR__ | ||||
| 
 | ||||
| #include <iostream> | ||||
| #include <map> | ||||
| #include <vector> | ||||
| 
 | ||||
| #include <boost/serialization/serialization.hpp> | ||||
| #include <boost/serialization/map.hpp> | ||||
| 
 | ||||
| namespace DBoW2 { | ||||
| 
 | ||||
| /// Id of words
 | ||||
| typedef unsigned int WordId; | ||||
| 
 | ||||
| /// Value of a word
 | ||||
| typedef double WordValue; | ||||
| 
 | ||||
| /// Id of nodes in the vocabulary treee
 | ||||
| typedef unsigned int NodeId; | ||||
| 
 | ||||
| /// L-norms for normalization
 | ||||
| enum LNorm | ||||
| { | ||||
|   L1, | ||||
|   L2 | ||||
| }; | ||||
| 
 | ||||
| /// Weighting type
 | ||||
| enum WeightingType | ||||
| { | ||||
|   TF_IDF, | ||||
|   TF, | ||||
|   IDF, | ||||
|   BINARY | ||||
| }; | ||||
| 
 | ||||
| /// Scoring type
 | ||||
| enum ScoringType | ||||
| { | ||||
|   L1_NORM, | ||||
|   L2_NORM, | ||||
|   CHI_SQUARE, | ||||
|   KL, | ||||
|   BHATTACHARYYA, | ||||
|   DOT_PRODUCT, | ||||
| }; | ||||
| 
 | ||||
| /// Vector of words to represent images
 | ||||
| class BowVector:  | ||||
| 	public std::map<WordId, WordValue> | ||||
| { | ||||
|     friend class boost::serialization::access; | ||||
|     template<class Archive> | ||||
|     void serialize(Archive& ar, const int version) | ||||
|     { | ||||
|         ar & boost::serialization::base_object<std::map<WordId, WordValue> >(*this); | ||||
|     } | ||||
| 
 | ||||
| public: | ||||
| 
 | ||||
| 	/** 
 | ||||
| 	 * Constructor | ||||
| 	 */ | ||||
| 	BowVector(void); | ||||
| 
 | ||||
| 	/**
 | ||||
| 	 * Destructor | ||||
| 	 */ | ||||
| 	~BowVector(void); | ||||
| 	 | ||||
| 	/**
 | ||||
| 	 * Adds a value to a word value existing in the vector, or creates a new | ||||
| 	 * word with the given value | ||||
| 	 * @param id word id to look for | ||||
| 	 * @param v value to create the word with, or to add to existing word | ||||
| 	 */ | ||||
| 	void addWeight(WordId id, WordValue v); | ||||
| 	 | ||||
| 	/**
 | ||||
| 	 * Adds a word with a value to the vector only if this does not exist yet | ||||
| 	 * @param id word id to look for | ||||
| 	 * @param v value to give to the word if this does not exist | ||||
| 	 */ | ||||
| 	void addIfNotExist(WordId id, WordValue v); | ||||
| 
 | ||||
| 	/**
 | ||||
| 	 * L1-Normalizes the values in the vector  | ||||
| 	 * @param norm_type norm used | ||||
| 	 */ | ||||
| 	void normalize(LNorm norm_type); | ||||
| 	 | ||||
| 	/**
 | ||||
| 	 * Prints the content of the bow vector | ||||
| 	 * @param out stream | ||||
| 	 * @param v | ||||
| 	 */ | ||||
| 	friend std::ostream& operator<<(std::ostream &out, const BowVector &v); | ||||
| 	 | ||||
| 	/**
 | ||||
| 	 * Saves the bow vector as a vector in a matlab file | ||||
| 	 * @param filename | ||||
| 	 * @param W number of words in the vocabulary | ||||
| 	 */ | ||||
| 	void saveM(const std::string &filename, size_t W) const; | ||||
| }; | ||||
| 
 | ||||
| } // namespace DBoW2
 | ||||
| 
 | ||||
| #endif | ||||
							
								
								
									
										71
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/FClass.h
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										71
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/FClass.h
									
									
									
									
										vendored
									
									
								
							| @ -1,71 +0,0 @@ | ||||
| /**
 | ||||
|  * File: FClass.h | ||||
|  * Date: November 2011 | ||||
|  * Author: Dorian Galvez-Lopez | ||||
|  * Description: generic FClass to instantiate templated classes | ||||
|  * License: see the LICENSE.txt file | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #ifndef __D_T_FCLASS__ | ||||
| #define __D_T_FCLASS__ | ||||
| 
 | ||||
| #include <opencv2/core/core.hpp> | ||||
| #include <vector> | ||||
| #include <string> | ||||
| 
 | ||||
| namespace DBoW2 { | ||||
| 
 | ||||
| /// Generic class to encapsulate functions to manage descriptors.
 | ||||
| /**
 | ||||
|  * This class must be inherited. Derived classes can be used as the | ||||
|  * parameter F when creating Templated structures | ||||
|  * (TemplatedVocabulary, TemplatedDatabase, ...) | ||||
|  */ | ||||
| class FClass | ||||
| { | ||||
|   class TDescriptor; | ||||
|   typedef const TDescriptor *pDescriptor; | ||||
|    | ||||
|   /**
 | ||||
|    * Calculates the mean value of a set of descriptors | ||||
|    * @param descriptors | ||||
|    * @param mean mean descriptor | ||||
|    */ | ||||
|   virtual void meanValue(const std::vector<pDescriptor> &descriptors,  | ||||
|     TDescriptor &mean) = 0; | ||||
|    | ||||
|   /**
 | ||||
|    * Calculates the distance between two descriptors | ||||
|    * @param a | ||||
|    * @param b | ||||
|    * @return distance | ||||
|    */ | ||||
|   static double distance(const TDescriptor &a, const TDescriptor &b); | ||||
|    | ||||
|   /**
 | ||||
|    * Returns a string version of the descriptor | ||||
|    * @param a descriptor | ||||
|    * @return string version | ||||
|    */ | ||||
|   static std::string toString(const TDescriptor &a); | ||||
|    | ||||
|   /**
 | ||||
|    * Returns a descriptor from a string | ||||
|    * @param a descriptor | ||||
|    * @param s string version | ||||
|    */ | ||||
|   static void fromString(TDescriptor &a, const std::string &s); | ||||
| 
 | ||||
|   /**
 | ||||
|    * Returns a mat with the descriptors in float format | ||||
|    * @param descriptors | ||||
|    * @param mat (out) NxL 32F matrix | ||||
|    */ | ||||
|   static void toMat32F(const std::vector<TDescriptor> &descriptors,  | ||||
|     cv::Mat &mat); | ||||
| }; | ||||
| 
 | ||||
| } // namespace DBoW2
 | ||||
| 
 | ||||
| #endif | ||||
							
								
								
									
										193
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/FORB.cpp
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										193
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/FORB.cpp
									
									
									
									
										vendored
									
									
								
							| @ -1,193 +0,0 @@ | ||||
| /**
 | ||||
|  * File: FORB.cpp | ||||
|  * Date: June 2012 | ||||
|  * Author: Dorian Galvez-Lopez | ||||
|  * Description: functions for ORB descriptors | ||||
|  * License: see the LICENSE.txt file | ||||
|  * | ||||
|  * Distance function has been modified  | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
|   | ||||
| #include <vector> | ||||
| #include <string> | ||||
| #include <sstream> | ||||
| #include <stdint-gcc.h> | ||||
| 
 | ||||
| #include "FORB.h" | ||||
| 
 | ||||
| using namespace std; | ||||
| 
 | ||||
| namespace DBoW2 { | ||||
| 
 | ||||
| // --------------------------------------------------------------------------
 | ||||
| 
 | ||||
| const int FORB::L=32; | ||||
| 
 | ||||
| void FORB::meanValue(const std::vector<FORB::pDescriptor> &descriptors,  | ||||
|   FORB::TDescriptor &mean) | ||||
| { | ||||
|   if(descriptors.empty()) | ||||
|   { | ||||
|     mean.release(); | ||||
|     return; | ||||
|   } | ||||
|   else if(descriptors.size() == 1) | ||||
|   { | ||||
|     mean = descriptors[0]->clone(); | ||||
|   } | ||||
|   else | ||||
|   { | ||||
|     vector<int> sum(FORB::L * 8, 0); | ||||
|      | ||||
|     for(size_t i = 0; i < descriptors.size(); ++i) | ||||
|     { | ||||
|       const cv::Mat &d = *descriptors[i]; | ||||
|       const unsigned char *p = d.ptr<unsigned char>(); | ||||
|        | ||||
|       for(int j = 0; j < d.cols; ++j, ++p) | ||||
|       { | ||||
|         if(*p & (1 << 7)) ++sum[ j*8     ]; | ||||
|         if(*p & (1 << 6)) ++sum[ j*8 + 1 ]; | ||||
|         if(*p & (1 << 5)) ++sum[ j*8 + 2 ]; | ||||
|         if(*p & (1 << 4)) ++sum[ j*8 + 3 ]; | ||||
|         if(*p & (1 << 3)) ++sum[ j*8 + 4 ]; | ||||
|         if(*p & (1 << 2)) ++sum[ j*8 + 5 ]; | ||||
|         if(*p & (1 << 1)) ++sum[ j*8 + 6 ]; | ||||
|         if(*p & (1))      ++sum[ j*8 + 7 ]; | ||||
|       } | ||||
|     } | ||||
|      | ||||
|     mean = cv::Mat::zeros(1, FORB::L, CV_8U); | ||||
|     unsigned char *p = mean.ptr<unsigned char>(); | ||||
|      | ||||
|     const int N2 = (int)descriptors.size() / 2 + descriptors.size() % 2; | ||||
|     for(size_t i = 0; i < sum.size(); ++i) | ||||
|     { | ||||
|       if(sum[i] >= N2) | ||||
|       { | ||||
|         // set bit
 | ||||
|         *p |= 1 << (7 - (i % 8)); | ||||
|       } | ||||
|        | ||||
|       if(i % 8 == 7) ++p; | ||||
|     } | ||||
|   } | ||||
| } | ||||
| 
 | ||||
| // --------------------------------------------------------------------------
 | ||||
|    | ||||
| int FORB::distance(const FORB::TDescriptor &a, | ||||
|   const FORB::TDescriptor &b) | ||||
| { | ||||
|   // Bit set count operation from
 | ||||
|   // http://graphics.stanford.edu/~seander/bithacks.html#CountBitsSetParallel
 | ||||
| 
 | ||||
|   const int *pa = a.ptr<int32_t>(); | ||||
|   const int *pb = b.ptr<int32_t>(); | ||||
| 
 | ||||
|   int dist=0; | ||||
| 
 | ||||
|   for(int i=0; i<8; i++, pa++, pb++) | ||||
|   { | ||||
|       unsigned  int v = *pa ^ *pb; | ||||
|       v = v - ((v >> 1) & 0x55555555); | ||||
|       v = (v & 0x33333333) + ((v >> 2) & 0x33333333); | ||||
|       dist += (((v + (v >> 4)) & 0xF0F0F0F) * 0x1010101) >> 24; | ||||
|   } | ||||
| 
 | ||||
|   return dist; | ||||
| } | ||||
| 
 | ||||
| // --------------------------------------------------------------------------
 | ||||
|    | ||||
| std::string FORB::toString(const FORB::TDescriptor &a) | ||||
| { | ||||
|   stringstream ss; | ||||
|   const unsigned char *p = a.ptr<unsigned char>(); | ||||
|    | ||||
|   for(int i = 0; i < a.cols; ++i, ++p) | ||||
|   { | ||||
|     ss << (int)*p << " "; | ||||
|   } | ||||
|    | ||||
|   return ss.str(); | ||||
| } | ||||
| 
 | ||||
| // --------------------------------------------------------------------------
 | ||||
|    | ||||
| void FORB::fromString(FORB::TDescriptor &a, const std::string &s) | ||||
| { | ||||
|   a.create(1, FORB::L, CV_8U); | ||||
|   unsigned char *p = a.ptr<unsigned char>(); | ||||
|    | ||||
|   stringstream ss(s); | ||||
|   for(int i = 0; i < FORB::L; ++i, ++p) | ||||
|   { | ||||
|     int n; | ||||
|     ss >> n; | ||||
|      | ||||
|     if(!ss.fail())  | ||||
|       *p = (unsigned char)n; | ||||
|   } | ||||
|    | ||||
| } | ||||
| 
 | ||||
| // --------------------------------------------------------------------------
 | ||||
| 
 | ||||
| void FORB::toMat32F(const std::vector<TDescriptor> &descriptors,  | ||||
|   cv::Mat &mat) | ||||
| { | ||||
|   if(descriptors.empty()) | ||||
|   { | ||||
|     mat.release(); | ||||
|     return; | ||||
|   } | ||||
|    | ||||
|   const size_t N = descriptors.size(); | ||||
|    | ||||
|   mat.create(N, FORB::L*8, CV_32F); | ||||
|   float *p = mat.ptr<float>(); | ||||
|    | ||||
|   for(size_t i = 0; i < N; ++i) | ||||
|   { | ||||
|     const int C = descriptors[i].cols; | ||||
|     const unsigned char *desc = descriptors[i].ptr<unsigned char>(); | ||||
|      | ||||
|     for(int j = 0; j < C; ++j, p += 8) | ||||
|     { | ||||
|       p[0] = (desc[j] & (1 << 7) ? 1 : 0); | ||||
|       p[1] = (desc[j] & (1 << 6) ? 1 : 0); | ||||
|       p[2] = (desc[j] & (1 << 5) ? 1 : 0); | ||||
|       p[3] = (desc[j] & (1 << 4) ? 1 : 0); | ||||
|       p[4] = (desc[j] & (1 << 3) ? 1 : 0); | ||||
|       p[5] = (desc[j] & (1 << 2) ? 1 : 0); | ||||
|       p[6] = (desc[j] & (1 << 1) ? 1 : 0); | ||||
|       p[7] = desc[j] & (1); | ||||
|     } | ||||
|   }  | ||||
| } | ||||
| 
 | ||||
| // --------------------------------------------------------------------------
 | ||||
| 
 | ||||
| void FORB::toMat8U(const std::vector<TDescriptor> &descriptors,  | ||||
|   cv::Mat &mat) | ||||
| { | ||||
|   mat.create(descriptors.size(), 32, CV_8U); | ||||
|    | ||||
|   unsigned char *p = mat.ptr<unsigned char>(); | ||||
|    | ||||
|   for(size_t i = 0; i < descriptors.size(); ++i, p += 32) | ||||
|   { | ||||
|     const unsigned char *d = descriptors[i].ptr<unsigned char>(); | ||||
|     std::copy(d, d+32, p); | ||||
|   } | ||||
|    | ||||
| } | ||||
| 
 | ||||
| // --------------------------------------------------------------------------
 | ||||
| 
 | ||||
| } // namespace DBoW2
 | ||||
| 
 | ||||
| 
 | ||||
							
								
								
									
										79
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/FORB.h
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										79
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/FORB.h
									
									
									
									
										vendored
									
									
								
							| @ -1,79 +0,0 @@ | ||||
| /**
 | ||||
|  * File: FORB.h | ||||
|  * Date: June 2012 | ||||
|  * Author: Dorian Galvez-Lopez | ||||
|  * Description: functions for ORB descriptors | ||||
|  * License: see the LICENSE.txt file | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #ifndef __D_T_F_ORB__ | ||||
| #define __D_T_F_ORB__ | ||||
| 
 | ||||
| #include <opencv2/core/core.hpp> | ||||
| #include <vector> | ||||
| #include <string> | ||||
| 
 | ||||
| #include "FClass.h" | ||||
| 
 | ||||
| namespace DBoW2 { | ||||
| 
 | ||||
| /// Functions to manipulate ORB descriptors
 | ||||
| class FORB: protected FClass | ||||
| { | ||||
| public: | ||||
| 
 | ||||
|   /// Descriptor type
 | ||||
|   typedef cv::Mat TDescriptor; // CV_8U
 | ||||
|   /// Pointer to a single descriptor
 | ||||
|   typedef const TDescriptor *pDescriptor; | ||||
|   /// Descriptor length (in bytes)
 | ||||
|   static const int L; | ||||
| 
 | ||||
|   /**
 | ||||
|    * Calculates the mean value of a set of descriptors | ||||
|    * @param descriptors | ||||
|    * @param mean mean descriptor | ||||
|    */ | ||||
|   static void meanValue(const std::vector<pDescriptor> &descriptors, | ||||
|     TDescriptor &mean); | ||||
| 
 | ||||
|   /**
 | ||||
|    * Calculates the distance between two descriptors | ||||
|    * @param a | ||||
|    * @param b | ||||
|    * @return distance | ||||
|    */ | ||||
|   static int distance(const TDescriptor &a, const TDescriptor &b); | ||||
| 
 | ||||
|   /**
 | ||||
|    * Returns a string version of the descriptor | ||||
|    * @param a descriptor | ||||
|    * @return string version | ||||
|    */ | ||||
|   static std::string toString(const TDescriptor &a); | ||||
| 
 | ||||
|   /**
 | ||||
|    * Returns a descriptor from a string | ||||
|    * @param a descriptor | ||||
|    * @param s string version | ||||
|    */ | ||||
|   static void fromString(TDescriptor &a, const std::string &s); | ||||
| 
 | ||||
|   /**
 | ||||
|    * Returns a mat with the descriptors in float format | ||||
|    * @param descriptors | ||||
|    * @param mat (out) NxL 32F matrix | ||||
|    */ | ||||
|   static void toMat32F(const std::vector<TDescriptor> &descriptors, | ||||
|     cv::Mat &mat); | ||||
| 
 | ||||
|   static void toMat8U(const std::vector<TDescriptor> &descriptors, | ||||
|     cv::Mat &mat); | ||||
| 
 | ||||
| }; | ||||
| 
 | ||||
| } // namespace DBoW2
 | ||||
| 
 | ||||
| #endif | ||||
| 
 | ||||
							
								
								
									
										85
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/FeatureVector.cpp
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										85
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/FeatureVector.cpp
									
									
									
									
										vendored
									
									
								
							| @ -1,85 +0,0 @@ | ||||
| /**
 | ||||
|  * File: FeatureVector.cpp | ||||
|  * Date: November 2011 | ||||
|  * Author: Dorian Galvez-Lopez | ||||
|  * Description: feature vector | ||||
|  * License: see the LICENSE.txt file | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #include "FeatureVector.h" | ||||
| #include <map> | ||||
| #include <vector> | ||||
| #include <iostream> | ||||
| 
 | ||||
| namespace DBoW2 { | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
| FeatureVector::FeatureVector(void) | ||||
| { | ||||
| } | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
| FeatureVector::~FeatureVector(void) | ||||
| { | ||||
| } | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
| void FeatureVector::addFeature(NodeId id, unsigned int i_feature) | ||||
| { | ||||
|   FeatureVector::iterator vit = this->lower_bound(id); | ||||
|    | ||||
|   if(vit != this->end() && vit->first == id) | ||||
|   { | ||||
|     vit->second.push_back(i_feature); | ||||
|   } | ||||
|   else | ||||
|   { | ||||
|     vit = this->insert(vit, FeatureVector::value_type(id,  | ||||
|       std::vector<unsigned int>() )); | ||||
|     vit->second.push_back(i_feature); | ||||
|   } | ||||
| } | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
| std::ostream& operator<<(std::ostream &out,  | ||||
|   const FeatureVector &v) | ||||
| { | ||||
|   if(!v.empty()) | ||||
|   { | ||||
|     FeatureVector::const_iterator vit = v.begin(); | ||||
|      | ||||
|     const std::vector<unsigned int>* f = &vit->second; | ||||
| 
 | ||||
|     out << "<" << vit->first << ": ["; | ||||
|     if(!f->empty()) out << (*f)[0]; | ||||
|     for(unsigned int i = 1; i < f->size(); ++i) | ||||
|     { | ||||
|       out << ", " << (*f)[i]; | ||||
|     } | ||||
|     out << "]>"; | ||||
|      | ||||
|     for(++vit; vit != v.end(); ++vit) | ||||
|     { | ||||
|       f = &vit->second; | ||||
|        | ||||
|       out << ", <" << vit->first << ": ["; | ||||
|       if(!f->empty()) out << (*f)[0]; | ||||
|       for(unsigned int i = 1; i < f->size(); ++i) | ||||
|       { | ||||
|         out << ", " << (*f)[i]; | ||||
|       } | ||||
|       out << "]>"; | ||||
|     } | ||||
|   } | ||||
|    | ||||
|   return out;   | ||||
| } | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
| } // namespace DBoW2
 | ||||
							
								
								
									
										66
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/FeatureVector.h
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										66
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/FeatureVector.h
									
									
									
									
										vendored
									
									
								
							| @ -1,66 +0,0 @@ | ||||
| /**
 | ||||
|  * File: FeatureVector.h | ||||
|  * Date: November 2011 | ||||
|  * Author: Dorian Galvez-Lopez | ||||
|  * Description: feature vector | ||||
|  * License: see the LICENSE.txt file | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #ifndef __D_T_FEATURE_VECTOR__ | ||||
| #define __D_T_FEATURE_VECTOR__ | ||||
| 
 | ||||
| #include "BowVector.h" | ||||
| #include <map> | ||||
| #include <vector> | ||||
| #include <iostream> | ||||
| 
 | ||||
| #include <boost/serialization/serialization.hpp> | ||||
| #include <boost/serialization/map.hpp> | ||||
| 
 | ||||
| namespace DBoW2 { | ||||
| 
 | ||||
| /// Vector of nodes with indexes of local features
 | ||||
| class FeatureVector:  | ||||
|   public std::map<NodeId, std::vector<unsigned int> > | ||||
| { | ||||
|     friend class boost::serialization::access; | ||||
|     template<class Archive> | ||||
|     void serialize(Archive& ar, const int version) | ||||
|     { | ||||
|         ar & boost::serialization::base_object<std::map<NodeId, std::vector<unsigned int> > >(*this); | ||||
|     } | ||||
| 
 | ||||
| public: | ||||
| 
 | ||||
|   /**
 | ||||
|    * Constructor | ||||
|    */ | ||||
|   FeatureVector(void); | ||||
|    | ||||
|   /**
 | ||||
|    * Destructor | ||||
|    */ | ||||
|   ~FeatureVector(void); | ||||
|    | ||||
|   /**
 | ||||
|    * Adds a feature to an existing node, or adds a new node with an initial | ||||
|    * feature | ||||
|    * @param id node id to add or to modify | ||||
|    * @param i_feature index of feature to add to the given node | ||||
|    */ | ||||
|   void addFeature(NodeId id, unsigned int i_feature); | ||||
| 
 | ||||
|   /**
 | ||||
|    * Sends a string versions of the feature vector through the stream | ||||
|    * @param out stream | ||||
|    * @param v feature vector | ||||
|    */ | ||||
|   friend std::ostream& operator<<(std::ostream &out, const FeatureVector &v); | ||||
|      | ||||
| }; | ||||
| 
 | ||||
| } // namespace DBoW2
 | ||||
| 
 | ||||
| #endif | ||||
| 
 | ||||
							
								
								
									
										315
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/ScoringObject.cpp
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										315
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/ScoringObject.cpp
									
									
									
									
										vendored
									
									
								
							| @ -1,315 +0,0 @@ | ||||
| /**
 | ||||
|  * File: ScoringObject.cpp | ||||
|  * Date: November 2011 | ||||
|  * Author: Dorian Galvez-Lopez | ||||
|  * Description: functions to compute bow scores  | ||||
|  * License: see the LICENSE.txt file | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #include <cfloat> | ||||
| #include "TemplatedVocabulary.h" | ||||
| #include "BowVector.h" | ||||
| 
 | ||||
| using namespace DBoW2; | ||||
| 
 | ||||
| // If you change the type of WordValue, make sure you change also the
 | ||||
| // epsilon value (this is needed by the KL method)
 | ||||
| const double GeneralScoring::LOG_EPS = log(DBL_EPSILON); // FLT_EPSILON
 | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
| double L1Scoring::score(const BowVector &v1, const BowVector &v2) const | ||||
| { | ||||
|   BowVector::const_iterator v1_it, v2_it; | ||||
|   const BowVector::const_iterator v1_end = v1.end(); | ||||
|   const BowVector::const_iterator v2_end = v2.end(); | ||||
|    | ||||
|   v1_it = v1.begin(); | ||||
|   v2_it = v2.begin(); | ||||
|    | ||||
|   double score = 0; | ||||
|    | ||||
|   while(v1_it != v1_end && v2_it != v2_end) | ||||
|   { | ||||
|     const WordValue& vi = v1_it->second; | ||||
|     const WordValue& wi = v2_it->second; | ||||
|      | ||||
|     if(v1_it->first == v2_it->first) | ||||
|     { | ||||
|       score += fabs(vi - wi) - fabs(vi) - fabs(wi); | ||||
|        | ||||
|       // move v1 and v2 forward
 | ||||
|       ++v1_it; | ||||
|       ++v2_it; | ||||
|     } | ||||
|     else if(v1_it->first < v2_it->first) | ||||
|     { | ||||
|       // move v1 forward
 | ||||
|       v1_it = v1.lower_bound(v2_it->first); | ||||
|       // v1_it = (first element >= v2_it.id)
 | ||||
|     } | ||||
|     else | ||||
|     { | ||||
|       // move v2 forward
 | ||||
|       v2_it = v2.lower_bound(v1_it->first); | ||||
|       // v2_it = (first element >= v1_it.id)
 | ||||
|     } | ||||
|   } | ||||
|    | ||||
|   // ||v - w||_{L1} = 2 + Sum(|v_i - w_i| - |v_i| - |w_i|) 
 | ||||
|   //		for all i | v_i != 0 and w_i != 0 
 | ||||
|   // (Nister, 2006)
 | ||||
|   // scaled_||v - w||_{L1} = 1 - 0.5 * ||v - w||_{L1}
 | ||||
|   score = -score/2.0; | ||||
| 
 | ||||
|   return score; // [0..1]
 | ||||
| } | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
| double L2Scoring::score(const BowVector &v1, const BowVector &v2) const | ||||
| { | ||||
|   BowVector::const_iterator v1_it, v2_it; | ||||
|   const BowVector::const_iterator v1_end = v1.end(); | ||||
|   const BowVector::const_iterator v2_end = v2.end(); | ||||
|    | ||||
|   v1_it = v1.begin(); | ||||
|   v2_it = v2.begin(); | ||||
|    | ||||
|   double score = 0; | ||||
|    | ||||
|   while(v1_it != v1_end && v2_it != v2_end) | ||||
|   { | ||||
|     const WordValue& vi = v1_it->second; | ||||
|     const WordValue& wi = v2_it->second; | ||||
|      | ||||
|     if(v1_it->first == v2_it->first) | ||||
|     { | ||||
|       score += vi * wi; | ||||
|        | ||||
|       // move v1 and v2 forward
 | ||||
|       ++v1_it; | ||||
|       ++v2_it; | ||||
|     } | ||||
|     else if(v1_it->first < v2_it->first) | ||||
|     { | ||||
|       // move v1 forward
 | ||||
|       v1_it = v1.lower_bound(v2_it->first); | ||||
|       // v1_it = (first element >= v2_it.id)
 | ||||
|     } | ||||
|     else | ||||
|     { | ||||
|       // move v2 forward
 | ||||
|       v2_it = v2.lower_bound(v1_it->first); | ||||
|       // v2_it = (first element >= v1_it.id)
 | ||||
|     } | ||||
|   } | ||||
|    | ||||
|   // ||v - w||_{L2} = sqrt( 2 - 2 * Sum(v_i * w_i) )
 | ||||
| 	//		for all i | v_i != 0 and w_i != 0 )
 | ||||
| 	// (Nister, 2006)
 | ||||
| 	if(score >= 1) // rounding errors
 | ||||
| 	  score = 1.0; | ||||
| 	else | ||||
|     score = 1.0 - sqrt(1.0 - score); // [0..1]
 | ||||
| 
 | ||||
|   return score; | ||||
| } | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
| double ChiSquareScoring::score(const BowVector &v1, const BowVector &v2)  | ||||
|   const | ||||
| { | ||||
|   BowVector::const_iterator v1_it, v2_it; | ||||
|   const BowVector::const_iterator v1_end = v1.end(); | ||||
|   const BowVector::const_iterator v2_end = v2.end(); | ||||
|    | ||||
|   v1_it = v1.begin(); | ||||
|   v2_it = v2.begin(); | ||||
|    | ||||
|   double score = 0; | ||||
|    | ||||
|   // all the items are taken into account
 | ||||
|    | ||||
|   while(v1_it != v1_end && v2_it != v2_end) | ||||
|   { | ||||
|     const WordValue& vi = v1_it->second; | ||||
|     const WordValue& wi = v2_it->second; | ||||
|      | ||||
|     if(v1_it->first == v2_it->first) | ||||
|     { | ||||
|       // (v-w)^2/(v+w) - v - w = -4 vw/(v+w)
 | ||||
|       // we move the -4 out
 | ||||
|       if(vi + wi != 0.0) score += vi * wi / (vi + wi); | ||||
|        | ||||
|       // move v1 and v2 forward
 | ||||
|       ++v1_it; | ||||
|       ++v2_it; | ||||
|     } | ||||
|     else if(v1_it->first < v2_it->first) | ||||
|     { | ||||
|       // move v1 forward
 | ||||
|       v1_it = v1.lower_bound(v2_it->first); | ||||
|     } | ||||
|     else | ||||
|     { | ||||
|       // move v2 forward
 | ||||
|       v2_it = v2.lower_bound(v1_it->first); | ||||
|     } | ||||
|   } | ||||
|      | ||||
|   // this takes the -4 into account
 | ||||
|   score = 2. * score; // [0..1]
 | ||||
| 
 | ||||
|   return score; | ||||
| } | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
| double KLScoring::score(const BowVector &v1, const BowVector &v2) const | ||||
| {  | ||||
|   BowVector::const_iterator v1_it, v2_it; | ||||
|   const BowVector::const_iterator v1_end = v1.end(); | ||||
|   const BowVector::const_iterator v2_end = v2.end(); | ||||
|    | ||||
|   v1_it = v1.begin(); | ||||
|   v2_it = v2.begin(); | ||||
|    | ||||
|   double score = 0; | ||||
|    | ||||
|   // all the items or v are taken into account
 | ||||
|    | ||||
|   while(v1_it != v1_end && v2_it != v2_end) | ||||
|   { | ||||
|     const WordValue& vi = v1_it->second; | ||||
|     const WordValue& wi = v2_it->second; | ||||
|      | ||||
|     if(v1_it->first == v2_it->first) | ||||
|     { | ||||
|       if(vi != 0 && wi != 0) score += vi * log(vi/wi); | ||||
|        | ||||
|       // move v1 and v2 forward
 | ||||
|       ++v1_it; | ||||
|       ++v2_it; | ||||
|     } | ||||
|     else if(v1_it->first < v2_it->first) | ||||
|     { | ||||
|       // move v1 forward
 | ||||
|       score += vi * (log(vi) - LOG_EPS); | ||||
|       ++v1_it; | ||||
|     } | ||||
|     else | ||||
|     { | ||||
|       // move v2_it forward, do not add any score
 | ||||
|       v2_it = v2.lower_bound(v1_it->first); | ||||
|       // v2_it = (first element >= v1_it.id)
 | ||||
|     } | ||||
|   } | ||||
|    | ||||
|   // sum rest of items of v
 | ||||
|   for(; v1_it != v1_end; ++v1_it)  | ||||
|     if(v1_it->second != 0) | ||||
|       score += v1_it->second * (log(v1_it->second) - LOG_EPS); | ||||
|    | ||||
|   return score; // cannot be scaled
 | ||||
| } | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
| double BhattacharyyaScoring::score(const BowVector &v1,  | ||||
|   const BowVector &v2) const | ||||
| { | ||||
|   BowVector::const_iterator v1_it, v2_it; | ||||
|   const BowVector::const_iterator v1_end = v1.end(); | ||||
|   const BowVector::const_iterator v2_end = v2.end(); | ||||
|    | ||||
|   v1_it = v1.begin(); | ||||
|   v2_it = v2.begin(); | ||||
|    | ||||
|   double score = 0; | ||||
|    | ||||
|   while(v1_it != v1_end && v2_it != v2_end) | ||||
|   { | ||||
|     const WordValue& vi = v1_it->second; | ||||
|     const WordValue& wi = v2_it->second; | ||||
|      | ||||
|     if(v1_it->first == v2_it->first) | ||||
|     { | ||||
|       score += sqrt(vi * wi); | ||||
|        | ||||
|       // move v1 and v2 forward
 | ||||
|       ++v1_it; | ||||
|       ++v2_it; | ||||
|     } | ||||
|     else if(v1_it->first < v2_it->first) | ||||
|     { | ||||
|       // move v1 forward
 | ||||
|       v1_it = v1.lower_bound(v2_it->first); | ||||
|       // v1_it = (first element >= v2_it.id)
 | ||||
|     } | ||||
|     else | ||||
|     { | ||||
|       // move v2 forward
 | ||||
|       v2_it = v2.lower_bound(v1_it->first); | ||||
|       // v2_it = (first element >= v1_it.id)
 | ||||
|     } | ||||
|   } | ||||
| 
 | ||||
|   return score; // already scaled
 | ||||
| } | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
| double DotProductScoring::score(const BowVector &v1,  | ||||
|   const BowVector &v2) const | ||||
| { | ||||
|   BowVector::const_iterator v1_it, v2_it; | ||||
|   const BowVector::const_iterator v1_end = v1.end(); | ||||
|   const BowVector::const_iterator v2_end = v2.end(); | ||||
|    | ||||
|   v1_it = v1.begin(); | ||||
|   v2_it = v2.begin(); | ||||
|    | ||||
|   double score = 0; | ||||
|    | ||||
|   while(v1_it != v1_end && v2_it != v2_end) | ||||
|   { | ||||
|     const WordValue& vi = v1_it->second; | ||||
|     const WordValue& wi = v2_it->second; | ||||
|      | ||||
|     if(v1_it->first == v2_it->first) | ||||
|     { | ||||
|       score += vi * wi; | ||||
|        | ||||
|       // move v1 and v2 forward
 | ||||
|       ++v1_it; | ||||
|       ++v2_it; | ||||
|     } | ||||
|     else if(v1_it->first < v2_it->first) | ||||
|     { | ||||
|       // move v1 forward
 | ||||
|       v1_it = v1.lower_bound(v2_it->first); | ||||
|       // v1_it = (first element >= v2_it.id)
 | ||||
|     } | ||||
|     else | ||||
|     { | ||||
|       // move v2 forward
 | ||||
|       v2_it = v2.lower_bound(v1_it->first); | ||||
|       // v2_it = (first element >= v1_it.id)
 | ||||
|     } | ||||
|   } | ||||
| 
 | ||||
|   return score; // cannot scale
 | ||||
| } | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
							
								
								
									
										96
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/ScoringObject.h
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										96
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/ScoringObject.h
									
									
									
									
										vendored
									
									
								
							| @ -1,96 +0,0 @@ | ||||
| /**
 | ||||
|  * File: ScoringObject.h | ||||
|  * Date: November 2011 | ||||
|  * Author: Dorian Galvez-Lopez | ||||
|  * Description: functions to compute bow scores  | ||||
|  * License: see the LICENSE.txt file | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #ifndef __D_T_SCORING_OBJECT__ | ||||
| #define __D_T_SCORING_OBJECT__ | ||||
| 
 | ||||
| #include "BowVector.h" | ||||
| 
 | ||||
| namespace DBoW2 { | ||||
| 
 | ||||
| /// Base class of scoring functions
 | ||||
| class GeneralScoring | ||||
| { | ||||
| public: | ||||
|   /**
 | ||||
|    * Computes the score between two vectors. Vectors must be sorted and  | ||||
|    * normalized if necessary | ||||
|    * @param v (in/out) | ||||
|    * @param w (in/out) | ||||
|    * @return score | ||||
|    */ | ||||
|   virtual double score(const BowVector &v, const BowVector &w) const = 0; | ||||
| 
 | ||||
|   /**
 | ||||
|    * Returns whether a vector must be normalized before scoring according | ||||
|    * to the scoring scheme | ||||
|    * @param norm norm to use | ||||
|    * @return true iff must normalize | ||||
|    */ | ||||
|   virtual bool mustNormalize(LNorm &norm) const = 0; | ||||
| 
 | ||||
|   /// Log of epsilon
 | ||||
| 	static const double LOG_EPS;  | ||||
|   // If you change the type of WordValue, make sure you change also the
 | ||||
| 	// epsilon value (this is needed by the KL method)
 | ||||
| 
 | ||||
|   virtual ~GeneralScoring() {} //!< Required for virtual base classes
 | ||||
| 	 | ||||
| }; | ||||
| 
 | ||||
| /** 
 | ||||
|  * Macro for defining Scoring classes | ||||
|  * @param NAME name of class | ||||
|  * @param MUSTNORMALIZE if vectors must be normalized to compute the score | ||||
|  * @param NORM type of norm to use when MUSTNORMALIZE | ||||
|  */ | ||||
| #define __SCORING_CLASS(NAME, MUSTNORMALIZE, NORM) \ | ||||
|   NAME: public GeneralScoring \ | ||||
|   { public: \ | ||||
|     /** \
 | ||||
|      * Computes score between two vectors \ | ||||
|      * @param v \ | ||||
|      * @param w \ | ||||
|      * @return score between v and w \ | ||||
|      */ \ | ||||
|     virtual double score(const BowVector &v, const BowVector &w) const; \ | ||||
|     \ | ||||
|     /** \
 | ||||
|      * Says if a vector must be normalized according to the scoring function \ | ||||
|      * @param norm (out) if true, norm to use | ||||
|      * @return true iff vectors must be normalized \ | ||||
|      */ \ | ||||
|     virtual inline bool mustNormalize(LNorm &norm) const  \ | ||||
|       { norm = NORM; return MUSTNORMALIZE; } \ | ||||
|   } | ||||
|    | ||||
| /// L1 Scoring object
 | ||||
| class __SCORING_CLASS(L1Scoring, true, L1); | ||||
| 
 | ||||
| /// L2 Scoring object
 | ||||
| class __SCORING_CLASS(L2Scoring, true, L2); | ||||
| 
 | ||||
| /// Chi square Scoring object
 | ||||
| class __SCORING_CLASS(ChiSquareScoring, true, L1); | ||||
| 
 | ||||
| /// KL divergence Scoring object
 | ||||
| class __SCORING_CLASS(KLScoring, true, L1); | ||||
| 
 | ||||
| /// Bhattacharyya Scoring object
 | ||||
| class __SCORING_CLASS(BhattacharyyaScoring, true, L1); | ||||
| 
 | ||||
| /// Dot product Scoring object
 | ||||
| class __SCORING_CLASS(DotProductScoring, false, L1); | ||||
| 
 | ||||
| #undef __SCORING_CLASS | ||||
|    | ||||
| } // namespace DBoW2
 | ||||
| 
 | ||||
| #endif | ||||
| 
 | ||||
							
								
								
									
										1665
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/TemplatedVocabulary.h
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										1665
									
								
								SLAM/Thirdparty/DBoW2/DBoW2/TemplatedVocabulary.h
									
									
									
									
										vendored
									
									
								
							
										
											
												File diff suppressed because it is too large
												Load Diff
											
										
									
								
							
							
								
								
									
										129
									
								
								SLAM/Thirdparty/DBoW2/DUtils/Random.cpp
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										129
									
								
								SLAM/Thirdparty/DBoW2/DUtils/Random.cpp
									
									
									
									
										vendored
									
									
								
							| @ -1,129 +0,0 @@ | ||||
| /*	
 | ||||
|  * File: Random.cpp | ||||
|  * Project: DUtils library | ||||
|  * Author: Dorian Galvez-Lopez | ||||
|  * Date: April 2010 | ||||
|  * Description: manages pseudo-random numbers | ||||
|  * License: see the LICENSE.txt file | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #include "Random.h" | ||||
| #include "Timestamp.h" | ||||
| #include <cstdlib> | ||||
| using namespace std; | ||||
| 
 | ||||
| bool DUtils::Random::m_already_seeded = false; | ||||
| 
 | ||||
| void DUtils::Random::SeedRand(){ | ||||
| 	Timestamp time; | ||||
| 	time.setToCurrentTime(); | ||||
| 	srand((unsigned)time.getFloatTime());  | ||||
| } | ||||
| 
 | ||||
| void DUtils::Random::SeedRandOnce() | ||||
| { | ||||
|   if(!m_already_seeded) | ||||
|   { | ||||
|     DUtils::Random::SeedRand(); | ||||
|     m_already_seeded = true; | ||||
|   } | ||||
| } | ||||
| 
 | ||||
| void DUtils::Random::SeedRand(int seed) | ||||
| { | ||||
| 	srand(seed);  | ||||
| } | ||||
| 
 | ||||
| void DUtils::Random::SeedRandOnce(int seed) | ||||
| { | ||||
|   if(!m_already_seeded) | ||||
|   { | ||||
|     DUtils::Random::SeedRand(seed); | ||||
|     m_already_seeded = true; | ||||
|   } | ||||
| } | ||||
| 
 | ||||
| int DUtils::Random::RandomInt(int min, int max){ | ||||
| 	int d = max - min + 1; | ||||
| 	return int(((double)rand()/((double)RAND_MAX + 1.0)) * d) + min; | ||||
| } | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
| DUtils::Random::UnrepeatedRandomizer::UnrepeatedRandomizer(int min, int max) | ||||
| { | ||||
|   if(min <= max) | ||||
|   { | ||||
|     m_min = min; | ||||
|     m_max = max; | ||||
|   } | ||||
|   else | ||||
|   { | ||||
|     m_min = max; | ||||
|     m_max = min; | ||||
|   } | ||||
| 
 | ||||
|   createValues(); | ||||
| } | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
| DUtils::Random::UnrepeatedRandomizer::UnrepeatedRandomizer | ||||
|   (const DUtils::Random::UnrepeatedRandomizer& rnd) | ||||
| { | ||||
|   *this = rnd; | ||||
| } | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
| int DUtils::Random::UnrepeatedRandomizer::get() | ||||
| { | ||||
|   if(empty()) createValues(); | ||||
|    | ||||
|   DUtils::Random::SeedRandOnce(); | ||||
|    | ||||
|   int k = DUtils::Random::RandomInt(0, m_values.size()-1); | ||||
|   int ret = m_values[k]; | ||||
|   m_values[k] = m_values.back(); | ||||
|   m_values.pop_back(); | ||||
|    | ||||
|   return ret; | ||||
| } | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
| void DUtils::Random::UnrepeatedRandomizer::createValues() | ||||
| { | ||||
|   int n = m_max - m_min + 1; | ||||
|    | ||||
|   m_values.resize(n); | ||||
|   for(int i = 0; i < n; ++i) m_values[i] = m_min + i; | ||||
| } | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
| void DUtils::Random::UnrepeatedRandomizer::reset() | ||||
| { | ||||
|   if((int)m_values.size() != m_max - m_min + 1) createValues(); | ||||
| } | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
| DUtils::Random::UnrepeatedRandomizer&  | ||||
| DUtils::Random::UnrepeatedRandomizer::operator= | ||||
|   (const DUtils::Random::UnrepeatedRandomizer& rnd) | ||||
| { | ||||
|   if(this != &rnd) | ||||
|   { | ||||
|     this->m_min = rnd.m_min; | ||||
|     this->m_max = rnd.m_max; | ||||
|     this->m_values = rnd.m_values; | ||||
|   } | ||||
|   return *this; | ||||
| } | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
| 
 | ||||
							
								
								
									
										184
									
								
								SLAM/Thirdparty/DBoW2/DUtils/Random.h
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										184
									
								
								SLAM/Thirdparty/DBoW2/DUtils/Random.h
									
									
									
									
										vendored
									
									
								
							| @ -1,184 +0,0 @@ | ||||
| /*	
 | ||||
|  * File: Random.h | ||||
|  * Project: DUtils library | ||||
|  * Author: Dorian Galvez-Lopez | ||||
|  * Date: April 2010, November 2011 | ||||
|  * Description: manages pseudo-random numbers | ||||
|  * License: see the LICENSE.txt file | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #pragma once | ||||
| #ifndef __D_RANDOM__ | ||||
| #define __D_RANDOM__ | ||||
| 
 | ||||
| #include <cstdlib> | ||||
| #include <vector> | ||||
| 
 | ||||
| namespace DUtils { | ||||
| 
 | ||||
| /// Functions to generate pseudo-random numbers
 | ||||
| class Random | ||||
| { | ||||
| public: | ||||
|   class UnrepeatedRandomizer; | ||||
|    | ||||
| public: | ||||
| 	/**
 | ||||
| 	 * Sets the random number seed to the current time | ||||
| 	 */ | ||||
| 	static void SeedRand(); | ||||
| 	 | ||||
| 	/**
 | ||||
| 	 * Sets the random number seed to the current time only the first | ||||
| 	 * time this function is called | ||||
| 	 */ | ||||
| 	static void SeedRandOnce(); | ||||
| 
 | ||||
| 	/** 
 | ||||
| 	 * Sets the given random number seed | ||||
| 	 * @param seed | ||||
| 	 */ | ||||
| 	static void SeedRand(int seed); | ||||
| 
 | ||||
| 	/** 
 | ||||
| 	 * Sets the given random number seed only the first time this function  | ||||
| 	 * is called | ||||
| 	 * @param seed | ||||
| 	 */ | ||||
| 	static void SeedRandOnce(int seed); | ||||
| 
 | ||||
| 	/**
 | ||||
| 	 * Returns a random number in the range [0..1] | ||||
| 	 * @return random T number in [0..1] | ||||
| 	 */ | ||||
| 	template <class T> | ||||
| 	static T RandomValue(){ | ||||
| 		return (T)rand()/(T)RAND_MAX; | ||||
| 	} | ||||
| 
 | ||||
| 	/**
 | ||||
| 	 * Returns a random number in the range [min..max] | ||||
| 	 * @param min | ||||
| 	 * @param max | ||||
| 	 * @return random T number in [min..max] | ||||
| 	 */ | ||||
| 	template <class T> | ||||
| 	static T RandomValue(T min, T max){ | ||||
| 		return Random::RandomValue<T>() * (max - min) + min; | ||||
| 	} | ||||
| 
 | ||||
| 	/**
 | ||||
| 	 * Returns a random int in the range [min..max] | ||||
| 	 * @param min | ||||
| 	 * @param max | ||||
| 	 * @return random int in [min..max] | ||||
| 	 */ | ||||
| 	static int RandomInt(int min, int max); | ||||
| 	 | ||||
| 	/** 
 | ||||
| 	 * Returns a random number from a gaussian distribution | ||||
| 	 * @param mean | ||||
| 	 * @param sigma standard deviation | ||||
| 	 */ | ||||
| 	template <class T> | ||||
| 	static T RandomGaussianValue(T mean, T sigma) | ||||
| 	{ | ||||
|     // Box-Muller transformation
 | ||||
|     T x1, x2, w, y1; | ||||
| 
 | ||||
|     do { | ||||
|       x1 = (T)2. * RandomValue<T>() - (T)1.; | ||||
|       x2 = (T)2. * RandomValue<T>() - (T)1.; | ||||
|       w = x1 * x1 + x2 * x2; | ||||
|     } while ( w >= (T)1. || w == (T)0. ); | ||||
| 
 | ||||
|     w = sqrt( ((T)-2.0 * log( w ) ) / w ); | ||||
|     y1 = x1 * w; | ||||
| 
 | ||||
|     return( mean + y1 * sigma ); | ||||
| 	} | ||||
| 
 | ||||
| private: | ||||
| 
 | ||||
|   /// If SeedRandOnce() or SeedRandOnce(int) have already been called
 | ||||
|   static bool m_already_seeded; | ||||
|    | ||||
| }; | ||||
| 
 | ||||
| // ---------------------------------------------------------------------------
 | ||||
| 
 | ||||
| /// Provides pseudo-random numbers with no repetitions
 | ||||
| class Random::UnrepeatedRandomizer | ||||
| { | ||||
| public: | ||||
| 
 | ||||
|   /** 
 | ||||
|    * Creates a randomizer that returns numbers in the range [min, max] | ||||
|    * @param min | ||||
|    * @param max | ||||
|    */ | ||||
|   UnrepeatedRandomizer(int min, int max); | ||||
|   ~UnrepeatedRandomizer(){} | ||||
|    | ||||
|   /**
 | ||||
|    * Copies a randomizer | ||||
|    * @param rnd | ||||
|    */ | ||||
|   UnrepeatedRandomizer(const UnrepeatedRandomizer& rnd); | ||||
|    | ||||
|   /**
 | ||||
|    * Copies a randomizer | ||||
|    * @param rnd | ||||
|    */ | ||||
|   UnrepeatedRandomizer& operator=(const UnrepeatedRandomizer& rnd); | ||||
|    | ||||
|   /** 
 | ||||
|    * Returns a random number not given before. If all the possible values | ||||
|    * were already given, the process starts again | ||||
|    * @return unrepeated random number | ||||
|    */ | ||||
|   int get(); | ||||
|    | ||||
|   /**
 | ||||
|    * Returns whether all the possible values between min and max were | ||||
|    * already given. If get() is called when empty() is true, the behaviour | ||||
|    * is the same than after creating the randomizer | ||||
|    * @return true iff all the values were returned | ||||
|    */ | ||||
|   inline bool empty() const { return m_values.empty(); } | ||||
|    | ||||
|   /**
 | ||||
|    * Returns the number of values still to be returned | ||||
|    * @return amount of values to return | ||||
|    */ | ||||
|   inline unsigned int left() const { return m_values.size(); } | ||||
|    | ||||
|   /**
 | ||||
|    * Resets the randomizer as it were just created | ||||
|    */ | ||||
|   void reset(); | ||||
|    | ||||
| protected: | ||||
| 
 | ||||
|   /** 
 | ||||
|    * Creates the vector with available values | ||||
|    */ | ||||
|   void createValues(); | ||||
| 
 | ||||
| protected: | ||||
| 
 | ||||
|   /// Min of range of values
 | ||||
|   int m_min; | ||||
|   /// Max of range of values
 | ||||
|   int m_max; | ||||
| 
 | ||||
|   /// Available values
 | ||||
|   std::vector<int> m_values; | ||||
| 
 | ||||
| }; | ||||
| 
 | ||||
| } | ||||
| 
 | ||||
| #endif | ||||
| 
 | ||||
							
								
								
									
										246
									
								
								SLAM/Thirdparty/DBoW2/DUtils/Timestamp.cpp
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										246
									
								
								SLAM/Thirdparty/DBoW2/DUtils/Timestamp.cpp
									
									
									
									
										vendored
									
									
								
							| @ -1,246 +0,0 @@ | ||||
| /*
 | ||||
|  * File: Timestamp.cpp | ||||
|  * Author: Dorian Galvez-Lopez | ||||
|  * Date: March 2009 | ||||
|  * Description: timestamping functions | ||||
|  *  | ||||
|  * Note: in windows, this class has a 1ms resolution | ||||
|  * | ||||
|  * License: see the LICENSE.txt file | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #include <cstdio> | ||||
| #include <cstdlib> | ||||
| #include <ctime> | ||||
| #include <cmath> | ||||
| #include <sstream> | ||||
| #include <iomanip> | ||||
| 
 | ||||
| #ifdef _WIN32 | ||||
| #ifndef WIN32 | ||||
| #define WIN32 | ||||
| #endif | ||||
| #endif | ||||
| 
 | ||||
| #ifdef WIN32 | ||||
| #include <sys/timeb.h> | ||||
| #define sprintf sprintf_s | ||||
| #else | ||||
| #include <sys/time.h> | ||||
| #endif | ||||
| 
 | ||||
| #include "Timestamp.h" | ||||
| 
 | ||||
| using namespace std; | ||||
| 
 | ||||
| using namespace DUtils; | ||||
| 
 | ||||
| Timestamp::Timestamp(Timestamp::tOptions option) | ||||
| { | ||||
|   if(option & CURRENT_TIME) | ||||
|     setToCurrentTime(); | ||||
|   else if(option & ZERO) | ||||
|     setTime(0.); | ||||
| } | ||||
| 
 | ||||
| Timestamp::~Timestamp(void) | ||||
| { | ||||
| } | ||||
| 
 | ||||
| bool Timestamp::empty() const | ||||
| { | ||||
|   return m_secs == 0 && m_usecs == 0; | ||||
| } | ||||
| 
 | ||||
| void Timestamp::setToCurrentTime(){ | ||||
| 	 | ||||
| #ifdef WIN32 | ||||
| 	struct __timeb32 timebuffer; | ||||
| 	_ftime32_s( &timebuffer ); // C4996
 | ||||
| 	// Note: _ftime is deprecated; consider using _ftime_s instead
 | ||||
| 	m_secs = timebuffer.time; | ||||
| 	m_usecs = timebuffer.millitm * 1000; | ||||
| #else | ||||
| 	struct timeval now; | ||||
| 	gettimeofday(&now, NULL); | ||||
| 	m_secs = now.tv_sec; | ||||
| 	m_usecs = now.tv_usec; | ||||
| #endif | ||||
| 
 | ||||
| } | ||||
| 
 | ||||
| void Timestamp::setTime(const string &stime){ | ||||
| 	string::size_type p = stime.find('.'); | ||||
| 	if(p == string::npos){ | ||||
| 		m_secs = atol(stime.c_str()); | ||||
| 		m_usecs = 0; | ||||
| 	}else{ | ||||
| 		m_secs = atol(stime.substr(0, p).c_str()); | ||||
| 		 | ||||
| 		string s_usecs = stime.substr(p+1, 6); | ||||
| 		m_usecs = atol(stime.substr(p+1).c_str()); | ||||
| 		m_usecs *= (unsigned long)pow(10.0, double(6 - s_usecs.length())); | ||||
| 	} | ||||
| } | ||||
| 
 | ||||
| void Timestamp::setTime(double s) | ||||
| { | ||||
|   m_secs = (unsigned long)s; | ||||
|   m_usecs = (s - (double)m_secs) * 1e6; | ||||
| } | ||||
| 
 | ||||
| double Timestamp::getFloatTime() const { | ||||
| 	return double(m_secs) + double(m_usecs)/1000000.0; | ||||
| } | ||||
| 
 | ||||
| string Timestamp::getStringTime() const { | ||||
| 	char buf[32]; | ||||
| 	sprintf(buf, "%.6lf", this->getFloatTime()); | ||||
| 	return string(buf); | ||||
| } | ||||
| 
 | ||||
| double Timestamp::operator- (const Timestamp &t) const { | ||||
| 	return this->getFloatTime() - t.getFloatTime(); | ||||
| } | ||||
| 
 | ||||
| Timestamp& Timestamp::operator+= (double s) | ||||
| { | ||||
|   *this = *this + s; | ||||
|   return *this; | ||||
| } | ||||
| 
 | ||||
| Timestamp& Timestamp::operator-= (double s) | ||||
| { | ||||
|   *this = *this - s; | ||||
|   return *this; | ||||
| } | ||||
| 
 | ||||
| Timestamp Timestamp::operator+ (double s) const | ||||
| { | ||||
| 	unsigned long secs = (long)floor(s); | ||||
| 	unsigned long usecs = (long)((s - (double)secs) * 1e6); | ||||
| 
 | ||||
|   return this->plus(secs, usecs); | ||||
| } | ||||
| 
 | ||||
| Timestamp Timestamp::plus(unsigned long secs, unsigned long usecs) const | ||||
| { | ||||
|   Timestamp t; | ||||
| 
 | ||||
| 	const unsigned long max = 1000000ul; | ||||
| 
 | ||||
| 	if(m_usecs + usecs >= max) | ||||
| 		t.setTime(m_secs + secs + 1, m_usecs + usecs - max); | ||||
| 	else | ||||
| 		t.setTime(m_secs + secs, m_usecs + usecs); | ||||
| 	 | ||||
| 	return t; | ||||
| } | ||||
| 
 | ||||
| Timestamp Timestamp::operator- (double s) const | ||||
| { | ||||
| 	unsigned long secs = (long)floor(s); | ||||
| 	unsigned long usecs = (long)((s - (double)secs) * 1e6); | ||||
| 
 | ||||
| 	return this->minus(secs, usecs); | ||||
| } | ||||
| 
 | ||||
| Timestamp Timestamp::minus(unsigned long secs, unsigned long usecs) const | ||||
| { | ||||
|   Timestamp t; | ||||
| 
 | ||||
| 	const unsigned long max = 1000000ul; | ||||
| 
 | ||||
| 	if(m_usecs < usecs) | ||||
| 		t.setTime(m_secs - secs - 1, max - (usecs - m_usecs)); | ||||
| 	else | ||||
| 		t.setTime(m_secs - secs, m_usecs - usecs); | ||||
| 	 | ||||
| 	return t; | ||||
| } | ||||
| 
 | ||||
| bool Timestamp::operator> (const Timestamp &t) const | ||||
| { | ||||
| 	if(m_secs > t.m_secs) return true; | ||||
| 	else if(m_secs == t.m_secs) return m_usecs > t.m_usecs; | ||||
| 	else return false; | ||||
| } | ||||
| 
 | ||||
| bool Timestamp::operator>= (const Timestamp &t) const | ||||
| { | ||||
| 	if(m_secs > t.m_secs) return true; | ||||
| 	else if(m_secs == t.m_secs) return m_usecs >= t.m_usecs; | ||||
| 	else return false; | ||||
| } | ||||
| 
 | ||||
| bool Timestamp::operator< (const Timestamp &t) const | ||||
| { | ||||
| 	if(m_secs < t.m_secs) return true; | ||||
| 	else if(m_secs == t.m_secs) return m_usecs < t.m_usecs; | ||||
| 	else return false; | ||||
| } | ||||
| 
 | ||||
| bool Timestamp::operator<= (const Timestamp &t) const | ||||
| { | ||||
| 	if(m_secs < t.m_secs) return true; | ||||
| 	else if(m_secs == t.m_secs) return m_usecs <= t.m_usecs; | ||||
| 	else return false; | ||||
| } | ||||
| 
 | ||||
| bool Timestamp::operator== (const Timestamp &t) const | ||||
| { | ||||
| 	return(m_secs == t.m_secs && m_usecs == t.m_usecs); | ||||
| } | ||||
| 
 | ||||
| 
 | ||||
| string Timestamp::Format(bool machine_friendly) const  | ||||
| { | ||||
|   struct tm tm_time; | ||||
| 
 | ||||
|   time_t t = (time_t)getFloatTime(); | ||||
| 
 | ||||
| #ifdef WIN32 | ||||
|   localtime_s(&tm_time, &t); | ||||
| #else | ||||
|   localtime_r(&t, &tm_time); | ||||
| #endif | ||||
|    | ||||
|   char buffer[128]; | ||||
|    | ||||
|   if(machine_friendly) | ||||
|   { | ||||
|     strftime(buffer, 128, "%Y%m%d_%H%M%S", &tm_time); | ||||
|   } | ||||
|   else | ||||
|   { | ||||
|     strftime(buffer, 128, "%c", &tm_time); // Thu Aug 23 14:55:02 2001
 | ||||
|   } | ||||
|    | ||||
|   return string(buffer); | ||||
| } | ||||
| 
 | ||||
| string Timestamp::Format(double s) { | ||||
| 	int days = int(s / (24. * 3600.0)); | ||||
| 	s -= days * (24. * 3600.0); | ||||
| 	int hours = int(s / 3600.0); | ||||
| 	s -= hours * 3600; | ||||
| 	int minutes = int(s / 60.0); | ||||
| 	s -= minutes * 60; | ||||
| 	int seconds = int(s); | ||||
| 	int ms = int((s - seconds)*1e6); | ||||
| 
 | ||||
| 	stringstream ss; | ||||
| 	ss.fill('0'); | ||||
| 	bool b; | ||||
| 	if((b = (days > 0))) ss << days << "d "; | ||||
| 	if((b = (b || hours > 0))) ss << setw(2) << hours << ":"; | ||||
| 	if((b = (b || minutes > 0))) ss << setw(2) << minutes << ":"; | ||||
| 	if(b) ss << setw(2); | ||||
| 	ss << seconds; | ||||
| 	if(!b) ss << "." << setw(6) << ms; | ||||
| 
 | ||||
| 	return ss.str(); | ||||
| } | ||||
| 
 | ||||
| 
 | ||||
							
								
								
									
										204
									
								
								SLAM/Thirdparty/DBoW2/DUtils/Timestamp.h
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										204
									
								
								SLAM/Thirdparty/DBoW2/DUtils/Timestamp.h
									
									
									
									
										vendored
									
									
								
							| @ -1,204 +0,0 @@ | ||||
| /*
 | ||||
|  * File: Timestamp.h | ||||
|  * Author: Dorian Galvez-Lopez | ||||
|  * Date: March 2009 | ||||
|  * Description: timestamping functions | ||||
|  * License: see the LICENSE.txt file | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #ifndef __D_TIMESTAMP__ | ||||
| #define __D_TIMESTAMP__ | ||||
| 
 | ||||
| #include <iostream> | ||||
| using namespace std; | ||||
| 
 | ||||
| namespace DUtils { | ||||
| 
 | ||||
| /// Timestamp
 | ||||
| class Timestamp | ||||
| { | ||||
| public: | ||||
| 
 | ||||
|   /// Options to initiate a timestamp
 | ||||
|   enum tOptions | ||||
|   { | ||||
|     NONE = 0, | ||||
|     CURRENT_TIME = 0x1, | ||||
|     ZERO = 0x2 | ||||
|   }; | ||||
|    | ||||
| public: | ||||
|    | ||||
|   /**
 | ||||
|    * Creates a timestamp  | ||||
|    * @param option option to set the initial time stamp | ||||
|    */ | ||||
| 	Timestamp(Timestamp::tOptions option = NONE); | ||||
| 	 | ||||
| 	/**
 | ||||
| 	 * Destructor | ||||
| 	 */ | ||||
| 	virtual ~Timestamp(void); | ||||
| 
 | ||||
|   /**
 | ||||
|    * Says if the timestamp is "empty": seconds and usecs are both 0, as  | ||||
|    * when initiated with the ZERO flag | ||||
|    * @return true iif secs == usecs == 0 | ||||
|    */ | ||||
|   bool empty() const; | ||||
| 
 | ||||
| 	/**
 | ||||
| 	 * Sets this instance to the current time | ||||
| 	 */ | ||||
| 	void setToCurrentTime(); | ||||
| 
 | ||||
| 	/**
 | ||||
| 	 * Sets the timestamp from seconds and microseconds | ||||
| 	 * @param secs: seconds | ||||
| 	 * @param usecs: microseconds | ||||
| 	 */ | ||||
| 	inline void setTime(unsigned long secs, unsigned long usecs){ | ||||
| 		m_secs = secs; | ||||
| 		m_usecs = usecs; | ||||
| 	} | ||||
| 	 | ||||
| 	/**
 | ||||
| 	 * Returns the timestamp in seconds and microseconds | ||||
| 	 * @param secs seconds | ||||
| 	 * @param usecs microseconds | ||||
| 	 */ | ||||
| 	inline void getTime(unsigned long &secs, unsigned long &usecs) const | ||||
| 	{ | ||||
| 	  secs = m_secs; | ||||
| 	  usecs = m_usecs; | ||||
| 	} | ||||
| 
 | ||||
| 	/**
 | ||||
| 	 * Sets the timestamp from a string with the time in seconds | ||||
| 	 * @param stime: string such as "1235603336.036609" | ||||
| 	 */ | ||||
| 	void setTime(const string &stime); | ||||
| 	 | ||||
| 	/**
 | ||||
| 	 * Sets the timestamp from a number of seconds from the epoch | ||||
| 	 * @param s seconds from the epoch | ||||
| 	 */ | ||||
| 	void setTime(double s); | ||||
| 	 | ||||
| 	/**
 | ||||
| 	 * Returns this timestamp as the number of seconds in (long) float format | ||||
| 	 */ | ||||
| 	double getFloatTime() const; | ||||
| 
 | ||||
| 	/**
 | ||||
| 	 * Returns this timestamp as the number of seconds in fixed length string format | ||||
| 	 */ | ||||
| 	string getStringTime() const; | ||||
| 
 | ||||
| 	/**
 | ||||
| 	 * Returns the difference in seconds between this timestamp (greater) and t (smaller) | ||||
| 	 * If the order is swapped, a negative number is returned | ||||
| 	 * @param t: timestamp to subtract from this timestamp | ||||
| 	 * @return difference in seconds | ||||
| 	 */ | ||||
| 	double operator- (const Timestamp &t) const; | ||||
| 
 | ||||
| 	/** 
 | ||||
| 	 * Returns a copy of this timestamp + s seconds + us microseconds | ||||
| 	 * @param s seconds | ||||
| 	 * @param us microseconds | ||||
| 	 */ | ||||
| 	Timestamp plus(unsigned long s, unsigned long us) const; | ||||
| 
 | ||||
|   /**
 | ||||
|    * Returns a copy of this timestamp - s seconds - us microseconds | ||||
|    * @param s seconds | ||||
|    * @param us microseconds | ||||
|    */ | ||||
|   Timestamp minus(unsigned long s, unsigned long us) const; | ||||
| 
 | ||||
|   /**
 | ||||
|    * Adds s seconds to this timestamp and returns a reference to itself | ||||
|    * @param s seconds | ||||
|    * @return reference to this timestamp | ||||
|    */ | ||||
|   Timestamp& operator+= (double s); | ||||
|    | ||||
|   /**
 | ||||
|    * Substracts s seconds to this timestamp and returns a reference to itself | ||||
|    * @param s seconds | ||||
|    * @return reference to this timestamp | ||||
|    */ | ||||
|   Timestamp& operator-= (double s); | ||||
| 
 | ||||
| 	/**
 | ||||
| 	 * Returns a copy of this timestamp + s seconds | ||||
| 	 * @param s: seconds | ||||
| 	 */ | ||||
| 	Timestamp operator+ (double s) const; | ||||
| 
 | ||||
| 	/**
 | ||||
| 	 * Returns a copy of this timestamp - s seconds | ||||
| 	 * @param s: seconds | ||||
| 	 */ | ||||
| 	Timestamp operator- (double s) const; | ||||
| 
 | ||||
| 	/**
 | ||||
| 	 * Returns whether this timestamp is at the future of t | ||||
| 	 * @param t | ||||
| 	 */ | ||||
| 	bool operator> (const Timestamp &t) const; | ||||
| 
 | ||||
| 	/**
 | ||||
| 	 * Returns whether this timestamp is at the future of (or is the same as) t | ||||
| 	 * @param t | ||||
| 	 */ | ||||
| 	bool operator>= (const Timestamp &t) const; | ||||
| 
 | ||||
| 	/** 
 | ||||
| 	 * Returns whether this timestamp and t represent the same instant | ||||
| 	 * @param t | ||||
| 	 */ | ||||
| 	bool operator== (const Timestamp &t) const; | ||||
| 
 | ||||
| 	/**
 | ||||
| 	 * Returns whether this timestamp is at the past of t | ||||
| 	 * @param t | ||||
| 	 */ | ||||
| 	bool operator< (const Timestamp &t) const; | ||||
| 
 | ||||
| 	/**
 | ||||
| 	 * Returns whether this timestamp is at the past of (or is the same as) t | ||||
| 	 * @param t | ||||
| 	 */ | ||||
| 	bool operator<= (const Timestamp &t) const; | ||||
| 
 | ||||
|   /**
 | ||||
|    * Returns the timestamp in a human-readable string | ||||
|    * @param machine_friendly if true, the returned string is formatted | ||||
|    *   to yyyymmdd_hhmmss, without weekday or spaces | ||||
|    * @note This has not been tested under Windows | ||||
|    * @note The timestamp is truncated to seconds | ||||
|    */ | ||||
|   string Format(bool machine_friendly = false) const; | ||||
| 
 | ||||
| 	/**
 | ||||
| 	 * Returns a string version of the elapsed time in seconds, with the format | ||||
| 	 * xd hh:mm:ss, hh:mm:ss, mm:ss or s.us | ||||
| 	 * @param s: elapsed seconds (given by getFloatTime) to format | ||||
| 	 */ | ||||
| 	static string Format(double s); | ||||
| 	 | ||||
| 
 | ||||
| protected: | ||||
|   /// Seconds
 | ||||
| 	unsigned long m_secs;	// seconds
 | ||||
| 	/// Microseconds
 | ||||
| 	unsigned long m_usecs;	// microseconds
 | ||||
| }; | ||||
| 
 | ||||
| } | ||||
| 
 | ||||
| #endif | ||||
| 
 | ||||
							
								
								
									
										7
									
								
								SLAM/Thirdparty/DBoW2/README.txt
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										7
									
								
								SLAM/Thirdparty/DBoW2/README.txt
									
									
									
									
										vendored
									
									
								
							| @ -1,7 +0,0 @@ | ||||
| You should have received this DBoW2 version along with ORB-SLAM2 (https://github.com/raulmur/ORB_SLAM2). | ||||
| See the original DBoW2 library at: https://github.com/dorian3d/DBoW2 | ||||
| All files included in this version are BSD, see LICENSE.txt | ||||
| 
 | ||||
| We also use Random.h, Random.cpp, Timestamp.pp and Timestamp.h from DLib/DUtils. | ||||
| See the original DLib library at: https://github.com/dorian3d/DLib | ||||
| All files included in this version are BSD, see LICENSE.txt | ||||
							
								
								
									
										178
									
								
								SLAM/Thirdparty/g2o/CMakeLists.txt
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										178
									
								
								SLAM/Thirdparty/g2o/CMakeLists.txt
									
									
									
									
										vendored
									
									
								
							| @ -1,178 +0,0 @@ | ||||
| CMAKE_MINIMUM_REQUIRED(VERSION 2.6) | ||||
| SET(CMAKE_LEGACY_CYGWIN_WIN32 0) | ||||
| 
 | ||||
| PROJECT(g2o) | ||||
| 
 | ||||
| SET(g2o_C_FLAGS) | ||||
| SET(g2o_CXX_FLAGS) | ||||
| 
 | ||||
| # default built type | ||||
| IF(NOT CMAKE_BUILD_TYPE) | ||||
|   SET(CMAKE_BUILD_TYPE Release) | ||||
| ENDIF() | ||||
| 
 | ||||
| MESSAGE(STATUS "BUILD TYPE:" ${CMAKE_BUILD_TYPE}) | ||||
| 
 | ||||
| SET (G2O_LIB_TYPE SHARED) | ||||
| 
 | ||||
| # There seems to be an issue with MSVC8 | ||||
| # see http://eigen.tuxfamily.org/bz/show_bug.cgi?id=83 | ||||
| if(MSVC90) | ||||
|   add_definitions(-DEIGEN_DONT_ALIGN_STATICALLY=1) | ||||
|   message(STATUS "Disabling memory alignment for MSVC8") | ||||
| endif(MSVC90) | ||||
| 
 | ||||
| # Set the output directory for the build executables and libraries | ||||
| IF(WIN32) | ||||
|   SET(g2o_LIBRARY_OUTPUT_DIRECTORY ${g2o_SOURCE_DIR}/bin CACHE PATH "Target for the libraries") | ||||
| ELSE(WIN32) | ||||
|   SET(g2o_LIBRARY_OUTPUT_DIRECTORY ${g2o_SOURCE_DIR}/lib CACHE PATH "Target for the libraries") | ||||
| ENDIF(WIN32) | ||||
| SET(CMAKE_ARCHIVE_OUTPUT_DIRECTORY ${g2o_LIBRARY_OUTPUT_DIRECTORY}) | ||||
| SET(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${g2o_LIBRARY_OUTPUT_DIRECTORY}) | ||||
| SET(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${g2o_RUNTIME_OUTPUT_DIRECTORY}) | ||||
| 
 | ||||
| # Set search directory for looking for our custom CMake scripts to | ||||
| # look for SuiteSparse, QGLViewer, and Eigen3. | ||||
| LIST(APPEND CMAKE_MODULE_PATH ${g2o_SOURCE_DIR}/cmake_modules) | ||||
| 
 | ||||
| # Detect OS and define macros appropriately | ||||
| IF(UNIX) | ||||
|   ADD_DEFINITIONS(-DUNIX) | ||||
|   MESSAGE(STATUS "Compiling on Unix") | ||||
| ENDIF(UNIX) | ||||
| 
 | ||||
| # Eigen library parallelise itself, though, presumably due to performance issues | ||||
| # OPENMP is experimental. We experienced some slowdown with it | ||||
| FIND_PACKAGE(OpenMP) | ||||
| SET(G2O_USE_OPENMP OFF CACHE BOOL "Build g2o with OpenMP support (EXPERIMENTAL)") | ||||
| IF(OPENMP_FOUND AND G2O_USE_OPENMP) | ||||
|   SET (G2O_OPENMP 1) | ||||
|   SET(g2o_C_FLAGS "${g2o_C_FLAGS} ${OpenMP_C_FLAGS}") | ||||
|   SET(g2o_CXX_FLAGS "${g2o_CXX_FLAGS} -DEIGEN_DONT_PARALLELIZE ${OpenMP_CXX_FLAGS}") | ||||
|   MESSAGE(STATUS "Compiling with OpenMP support") | ||||
| ENDIF(OPENMP_FOUND AND G2O_USE_OPENMP) | ||||
| 
 | ||||
| # Compiler specific options for gcc | ||||
| SET(CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS_RELEASE} -O3 -march=native") | ||||
| SET(CMAKE_C_FLAGS_RELEASE "${CMAKE_C_FLAGS_RELEASE} -O3 -march=native") | ||||
| # SET(CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS_RELEASE} -O3") | ||||
| # SET(CMAKE_C_FLAGS_RELEASE "${CMAKE_C_FLAGS_RELEASE} -O3") | ||||
| 
 | ||||
| # activate warnings !!! | ||||
| SET(g2o_C_FLAGS "${g2o_C_FLAGS} -Wall -W") | ||||
| SET(g2o_CXX_FLAGS "${g2o_CXX_FLAGS} -Wall -W") | ||||
| 
 | ||||
| # specifying compiler flags | ||||
| SET(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${g2o_CXX_FLAGS}") | ||||
| SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${g2o_C_FLAGS}") | ||||
| 
 | ||||
| # Find Eigen3 | ||||
| SET(EIGEN3_INCLUDE_DIR ${G2O_EIGEN3_INCLUDE}) | ||||
| FIND_PACKAGE(Eigen3 3.1.0 REQUIRED) | ||||
| IF(EIGEN3_FOUND) | ||||
|   SET(G2O_EIGEN3_INCLUDE ${EIGEN3_INCLUDE_DIR} CACHE PATH "Directory of Eigen3") | ||||
| ELSE(EIGEN3_FOUND) | ||||
|   SET(G2O_EIGEN3_INCLUDE "" CACHE PATH "Directory of Eigen3") | ||||
| ENDIF(EIGEN3_FOUND) | ||||
| 
 | ||||
| # Generate config.h | ||||
| SET(G2O_CXX_COMPILER "${CMAKE_CXX_COMPILER_ID} ${CMAKE_CXX_COMPILER}") | ||||
| configure_file(config.h.in ${g2o_SOURCE_DIR}/config.h) | ||||
| 
 | ||||
| # Set up the top-level include directories | ||||
| INCLUDE_DIRECTORIES( | ||||
| ${g2o_SOURCE_DIR}/core | ||||
| ${g2o_SOURCE_DIR}/types | ||||
| ${g2o_SOURCE_DIR}/stuff  | ||||
| ${G2O_EIGEN3_INCLUDE}) | ||||
| 
 | ||||
| # Include the subdirectories | ||||
| ADD_LIBRARY(g2o ${G2O_LIB_TYPE} | ||||
| #types | ||||
| g2o/types/types_sba.h | ||||
| g2o/types/types_six_dof_expmap.h | ||||
| g2o/types/types_sba.cpp | ||||
| g2o/types/types_six_dof_expmap.cpp | ||||
| g2o/types/types_seven_dof_expmap.cpp | ||||
| g2o/types/types_seven_dof_expmap.h | ||||
| g2o/types/se3quat.h | ||||
| g2o/types/se3_ops.h | ||||
| g2o/types/se3_ops.hpp | ||||
| #core | ||||
| g2o/core/base_edge.h | ||||
| g2o/core/base_binary_edge.h | ||||
| g2o/core/hyper_graph_action.cpp | ||||
| g2o/core/base_binary_edge.hpp | ||||
| g2o/core/hyper_graph_action.h | ||||
| g2o/core/base_multi_edge.h            | ||||
| g2o/core/hyper_graph.cpp | ||||
| g2o/core/base_multi_edge.hpp          | ||||
| g2o/core/hyper_graph.h | ||||
| g2o/core/base_unary_edge.h           | ||||
| g2o/core/linear_solver.h | ||||
| g2o/core/base_unary_edge.hpp          | ||||
| g2o/core/marginal_covariance_cholesky.cpp | ||||
| g2o/core/base_vertex.h                | ||||
| g2o/core/marginal_covariance_cholesky.h | ||||
| g2o/core/base_vertex.hpp              | ||||
| g2o/core/matrix_structure.cpp | ||||
| g2o/core/batch_stats.cpp              | ||||
| g2o/core/matrix_structure.h | ||||
| g2o/core/batch_stats.h                | ||||
| g2o/core/openmp_mutex.h | ||||
| g2o/core/block_solver.h               | ||||
| g2o/core/block_solver.hpp             | ||||
| g2o/core/parameter.cpp                | ||||
| g2o/core/parameter.h                  | ||||
| g2o/core/cache.cpp                    | ||||
| g2o/core/cache.h | ||||
| g2o/core/optimizable_graph.cpp        | ||||
| g2o/core/optimizable_graph.h          | ||||
| g2o/core/solver.cpp                   | ||||
| g2o/core/solver.h | ||||
| g2o/core/creators.h                  | ||||
| g2o/core/optimization_algorithm_factory.cpp | ||||
| g2o/core/estimate_propagator.cpp      | ||||
| g2o/core/optimization_algorithm_factory.h | ||||
| g2o/core/estimate_propagator.h        | ||||
| g2o/core/factory.cpp                  | ||||
| g2o/core/optimization_algorithm_property.h | ||||
| g2o/core/factory.h                    | ||||
| g2o/core/sparse_block_matrix.h | ||||
| g2o/core/sparse_optimizer.cpp   | ||||
| g2o/core/sparse_block_matrix.hpp | ||||
| g2o/core/sparse_optimizer.h | ||||
| g2o/core/hyper_dijkstra.cpp  | ||||
| g2o/core/hyper_dijkstra.h | ||||
| g2o/core/parameter_container.cpp      | ||||
| g2o/core/parameter_container.h | ||||
| g2o/core/optimization_algorithm.cpp  | ||||
| g2o/core/optimization_algorithm.h | ||||
| g2o/core/optimization_algorithm_with_hessian.cpp  | ||||
| g2o/core/optimization_algorithm_with_hessian.h | ||||
| g2o/core/optimization_algorithm_levenberg.cpp  | ||||
| g2o/core/optimization_algorithm_levenberg.h | ||||
| g2o/core/optimization_algorithm_gauss_newton.cpp  | ||||
| g2o/core/optimization_algorithm_gauss_newton.h | ||||
| g2o/core/jacobian_workspace.cpp  | ||||
| g2o/core/jacobian_workspace.h | ||||
| g2o/core/robust_kernel.cpp  | ||||
| g2o/core/robust_kernel.h | ||||
| g2o/core/robust_kernel_factory.cpp | ||||
| g2o/core/robust_kernel_factory.h | ||||
| g2o/core/robust_kernel_impl.cpp  | ||||
| g2o/core/robust_kernel_impl.h | ||||
| #stuff | ||||
| g2o/stuff/string_tools.h | ||||
| g2o/stuff/color_macros.h  | ||||
| g2o/stuff/macros.h | ||||
| g2o/stuff/timeutil.cpp | ||||
| g2o/stuff/misc.h | ||||
| g2o/stuff/timeutil.h | ||||
| g2o/stuff/os_specific.c     | ||||
| g2o/stuff/os_specific.h | ||||
| g2o/stuff/string_tools.cpp | ||||
| g2o/stuff/property.cpp        | ||||
| g2o/stuff/property.h        | ||||
| ) | ||||
							
								
								
									
										3
									
								
								SLAM/Thirdparty/g2o/README.txt
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										3
									
								
								SLAM/Thirdparty/g2o/README.txt
									
									
									
									
										vendored
									
									
								
							| @ -1,3 +0,0 @@ | ||||
| You should have received this g2o version along with ORB-SLAM2 (https://github.com/raulmur/ORB_SLAM2). | ||||
| See the original g2o library at: https://github.com/RainerKuemmerle/g2o | ||||
| All files included in this g2o version are BSD, see license-bsd.txt | ||||
							
								
								
									
										13
									
								
								SLAM/Thirdparty/g2o/config.h.in
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										13
									
								
								SLAM/Thirdparty/g2o/config.h.in
									
									
									
									
										vendored
									
									
								
							| @ -1,13 +0,0 @@ | ||||
| #ifndef G2O_CONFIG_H | ||||
| #define G2O_CONFIG_H | ||||
| 
 | ||||
| #cmakedefine G2O_OPENMP 1 | ||||
| #cmakedefine G2O_SHARED_LIBS 1 | ||||
| 
 | ||||
| // give a warning if Eigen defaults to row-major matrices.
 | ||||
| // We internally assume column-major matrices throughout the code.
 | ||||
| #ifdef EIGEN_DEFAULT_TO_ROW_MAJOR | ||||
| #  error "g2o requires column major Eigen matrices (see http://eigen.tuxfamily.org/bz/show_bug.cgi?id=422)"
 | ||||
| #endif | ||||
| 
 | ||||
| #endif | ||||
							
								
								
									
										119
									
								
								SLAM/Thirdparty/g2o/g2o/core/base_binary_edge.h
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										119
									
								
								SLAM/Thirdparty/g2o/g2o/core/base_binary_edge.h
									
									
									
									
										vendored
									
									
								
							| @ -1,119 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 R. Kuemmerle, G. Grisetti, H. Strasdat, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| #ifndef G2O_BASE_BINARY_EDGE_H | ||||
| #define G2O_BASE_BINARY_EDGE_H | ||||
| 
 | ||||
| #include <iostream> | ||||
| #include <limits> | ||||
| 
 | ||||
| #include "base_edge.h" | ||||
| #include "robust_kernel.h" | ||||
| #include "../../config.h" | ||||
| 
 | ||||
| namespace g2o { | ||||
| 
 | ||||
|   using namespace Eigen; | ||||
| 
 | ||||
|   template <int D, typename E, typename VertexXi, typename VertexXj> | ||||
|   class BaseBinaryEdge : public BaseEdge<D, E> | ||||
|   { | ||||
|     public: | ||||
| 
 | ||||
|       typedef VertexXi VertexXiType; | ||||
|       typedef VertexXj VertexXjType; | ||||
| 
 | ||||
|       static const int Di = VertexXiType::Dimension; | ||||
|       static const int Dj = VertexXjType::Dimension; | ||||
| 
 | ||||
|       static const int Dimension = BaseEdge<D, E>::Dimension; | ||||
|       typedef typename BaseEdge<D,E>::Measurement Measurement; | ||||
|       typedef typename Matrix<double, D, Di>::AlignedMapType JacobianXiOplusType; | ||||
|       typedef typename Matrix<double, D, Dj>::AlignedMapType JacobianXjOplusType; | ||||
|       typedef typename BaseEdge<D,E>::ErrorVector ErrorVector; | ||||
|       typedef typename BaseEdge<D,E>::InformationType InformationType; | ||||
| 
 | ||||
|       typedef Eigen::Map<Matrix<double, Di, Dj>, Matrix<double, Di, Dj>::Flags & AlignedBit ? Aligned : Unaligned > HessianBlockType; | ||||
|       typedef Eigen::Map<Matrix<double, Dj, Di>, Matrix<double, Dj, Di>::Flags & AlignedBit ? Aligned : Unaligned > HessianBlockTransposedType; | ||||
| 
 | ||||
|       BaseBinaryEdge() : BaseEdge<D,E>(), | ||||
|       _hessianRowMajor(false), | ||||
|       _hessian(0, VertexXiType::Dimension, VertexXjType::Dimension), // HACK we map to the null pointer for initializing the Maps
 | ||||
|       _hessianTransposed(0, VertexXjType::Dimension, VertexXiType::Dimension), | ||||
|       _jacobianOplusXi(0, D, Di), _jacobianOplusXj(0, D, Dj) | ||||
|       { | ||||
|         _vertices.resize(2); | ||||
|       } | ||||
| 
 | ||||
|       virtual OptimizableGraph::Vertex* createFrom(); | ||||
|       virtual OptimizableGraph::Vertex* createTo(); | ||||
| 
 | ||||
|       virtual void resize(size_t size); | ||||
| 
 | ||||
|       virtual bool allVerticesFixed() const; | ||||
| 
 | ||||
|       virtual void linearizeOplus(JacobianWorkspace& jacobianWorkspace); | ||||
| 
 | ||||
|       /**
 | ||||
|        * Linearizes the oplus operator in the vertex, and stores | ||||
|        * the result in temporary variables _jacobianOplusXi and _jacobianOplusXj | ||||
|        */ | ||||
|       virtual void linearizeOplus(); | ||||
| 
 | ||||
|       //! returns the result of the linearization in the manifold space for the node xi
 | ||||
|       const JacobianXiOplusType& jacobianOplusXi() const { return _jacobianOplusXi;} | ||||
|       //! returns the result of the linearization in the manifold space for the node xj
 | ||||
|       const JacobianXjOplusType& jacobianOplusXj() const { return _jacobianOplusXj;} | ||||
| 
 | ||||
|       virtual void constructQuadraticForm() ; | ||||
| 
 | ||||
|       virtual void mapHessianMemory(double* d, int i, int j, bool rowMajor); | ||||
| 
 | ||||
|       using BaseEdge<D,E>::resize; | ||||
|       using BaseEdge<D,E>::computeError; | ||||
| 
 | ||||
|     protected: | ||||
|       using BaseEdge<D,E>::_measurement; | ||||
|       using BaseEdge<D,E>::_information; | ||||
|       using BaseEdge<D,E>::_error; | ||||
|       using BaseEdge<D,E>::_vertices; | ||||
|       using BaseEdge<D,E>::_dimension; | ||||
| 
 | ||||
|       bool _hessianRowMajor; | ||||
|       HessianBlockType _hessian; | ||||
|       HessianBlockTransposedType _hessianTransposed; | ||||
|       JacobianXiOplusType _jacobianOplusXi; | ||||
|       JacobianXjOplusType _jacobianOplusXj; | ||||
| 
 | ||||
|     public: | ||||
|       EIGEN_MAKE_ALIGNED_OPERATOR_NEW | ||||
|   }; | ||||
| 
 | ||||
| #include "base_binary_edge.hpp" | ||||
| 
 | ||||
| } // end namespace g2o
 | ||||
| 
 | ||||
| #endif | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
							
								
								
									
										218
									
								
								SLAM/Thirdparty/g2o/g2o/core/base_binary_edge.hpp
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										218
									
								
								SLAM/Thirdparty/g2o/g2o/core/base_binary_edge.hpp
									
									
									
									
										vendored
									
									
								
							| @ -1,218 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 R. Kuemmerle, G. Grisetti, H. Strasdat, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| template <int D, typename E, typename VertexXiType, typename VertexXjType> | ||||
| OptimizableGraph::Vertex* BaseBinaryEdge<D, E, VertexXiType, VertexXjType>::createFrom(){ | ||||
|   return new VertexXiType(); | ||||
| } | ||||
| 
 | ||||
| template <int D, typename E, typename VertexXiType, typename VertexXjType> | ||||
| OptimizableGraph::Vertex* BaseBinaryEdge<D, E, VertexXiType, VertexXjType>::createTo(){ | ||||
|   return new VertexXjType(); | ||||
| } | ||||
| 
 | ||||
| 
 | ||||
| template <int D, typename E, typename VertexXiType, typename VertexXjType> | ||||
| void BaseBinaryEdge<D, E, VertexXiType, VertexXjType>::resize(size_t size) | ||||
| { | ||||
|   if (size != 2) { | ||||
|     std::cerr << "WARNING, attempting to resize binary edge " << BaseEdge<D, E>::id() << " to " << size << std::endl; | ||||
|   } | ||||
|   BaseEdge<D, E>::resize(size); | ||||
| } | ||||
| 
 | ||||
| template <int D, typename E, typename VertexXiType, typename VertexXjType> | ||||
| bool BaseBinaryEdge<D, E, VertexXiType, VertexXjType>::allVerticesFixed() const | ||||
| { | ||||
|   return (static_cast<const VertexXiType*> (_vertices[0])->fixed() && | ||||
|           static_cast<const VertexXjType*> (_vertices[1])->fixed()); | ||||
| } | ||||
| 
 | ||||
| template <int D, typename E, typename VertexXiType, typename VertexXjType> | ||||
| void BaseBinaryEdge<D, E, VertexXiType, VertexXjType>::constructQuadraticForm() | ||||
| { | ||||
|   VertexXiType* from = static_cast<VertexXiType*>(_vertices[0]); | ||||
|   VertexXjType* to   = static_cast<VertexXjType*>(_vertices[1]); | ||||
| 
 | ||||
|   // get the Jacobian of the nodes in the manifold domain
 | ||||
|   const JacobianXiOplusType& A = jacobianOplusXi(); | ||||
|   const JacobianXjOplusType& B = jacobianOplusXj(); | ||||
| 
 | ||||
| 
 | ||||
|   bool fromNotFixed = !(from->fixed()); | ||||
|   bool toNotFixed = !(to->fixed()); | ||||
| 
 | ||||
|   if (fromNotFixed || toNotFixed) { | ||||
| #ifdef G2O_OPENMP | ||||
|     from->lockQuadraticForm(); | ||||
|     to->lockQuadraticForm(); | ||||
| #endif | ||||
|     const InformationType& omega = _information; | ||||
|     Matrix<double, D, 1> omega_r = - omega * _error; | ||||
|     if (this->robustKernel() == 0) { | ||||
|       if (fromNotFixed) { | ||||
|         Matrix<double, VertexXiType::Dimension, D> AtO = A.transpose() * omega; | ||||
|         from->b().noalias() += A.transpose() * omega_r; | ||||
|         from->A().noalias() += AtO*A; | ||||
|         if (toNotFixed ) { | ||||
|           if (_hessianRowMajor) // we have to write to the block as transposed
 | ||||
|             _hessianTransposed.noalias() += B.transpose() * AtO.transpose(); | ||||
|           else | ||||
|             _hessian.noalias() += AtO * B; | ||||
|         } | ||||
|       }  | ||||
|       if (toNotFixed) { | ||||
|         to->b().noalias() += B.transpose() * omega_r; | ||||
|         to->A().noalias() += B.transpose() * omega * B; | ||||
|       } | ||||
|     } else { // robust (weighted) error according to some kernel
 | ||||
|       double error = this->chi2(); | ||||
|       Eigen::Vector3d rho; | ||||
|       this->robustKernel()->robustify(error, rho); | ||||
|       InformationType weightedOmega = this->robustInformation(rho); | ||||
|       //std::cout << PVAR(rho.transpose()) << std::endl;
 | ||||
|       //std::cout << PVAR(weightedOmega) << std::endl;
 | ||||
| 
 | ||||
|       omega_r *= rho[1]; | ||||
|       if (fromNotFixed) { | ||||
|         from->b().noalias() += A.transpose() * omega_r; | ||||
|         from->A().noalias() += A.transpose() * weightedOmega * A; | ||||
|         if (toNotFixed ) { | ||||
|           if (_hessianRowMajor) // we have to write to the block as transposed
 | ||||
|             _hessianTransposed.noalias() += B.transpose() * weightedOmega * A; | ||||
|           else | ||||
|             _hessian.noalias() += A.transpose() * weightedOmega * B; | ||||
|         } | ||||
|       }  | ||||
|       if (toNotFixed) { | ||||
|         to->b().noalias() += B.transpose() * omega_r; | ||||
|         to->A().noalias() += B.transpose() * weightedOmega * B; | ||||
|       } | ||||
|     } | ||||
| #ifdef G2O_OPENMP | ||||
|     to->unlockQuadraticForm(); | ||||
|     from->unlockQuadraticForm(); | ||||
| #endif | ||||
|   } | ||||
| } | ||||
| 
 | ||||
| template <int D, typename E, typename VertexXiType, typename VertexXjType> | ||||
| void BaseBinaryEdge<D, E, VertexXiType, VertexXjType>::linearizeOplus(JacobianWorkspace& jacobianWorkspace) | ||||
| { | ||||
|   new (&_jacobianOplusXi) JacobianXiOplusType(jacobianWorkspace.workspaceForVertex(0), D, Di); | ||||
|   new (&_jacobianOplusXj) JacobianXjOplusType(jacobianWorkspace.workspaceForVertex(1), D, Dj); | ||||
|   linearizeOplus(); | ||||
| } | ||||
| 
 | ||||
| template <int D, typename E, typename VertexXiType, typename VertexXjType> | ||||
| void BaseBinaryEdge<D, E, VertexXiType, VertexXjType>::linearizeOplus() | ||||
| { | ||||
|   VertexXiType* vi = static_cast<VertexXiType*>(_vertices[0]); | ||||
|   VertexXjType* vj = static_cast<VertexXjType*>(_vertices[1]); | ||||
| 
 | ||||
|   bool iNotFixed = !(vi->fixed()); | ||||
|   bool jNotFixed = !(vj->fixed()); | ||||
| 
 | ||||
|   if (!iNotFixed && !jNotFixed) | ||||
|     return; | ||||
| 
 | ||||
| #ifdef G2O_OPENMP | ||||
|   vi->lockQuadraticForm(); | ||||
|   vj->lockQuadraticForm(); | ||||
| #endif | ||||
| 
 | ||||
|   const double delta = 1e-9; | ||||
|   const double scalar = 1.0 / (2*delta); | ||||
|   ErrorVector errorBak; | ||||
|   ErrorVector errorBeforeNumeric = _error; | ||||
| 
 | ||||
|   if (iNotFixed) { | ||||
|     //Xi - estimate the jacobian numerically
 | ||||
|     double add_vi[VertexXiType::Dimension]; | ||||
|     std::fill(add_vi, add_vi + VertexXiType::Dimension, 0.0); | ||||
|     // add small step along the unit vector in each dimension
 | ||||
|     for (int d = 0; d < VertexXiType::Dimension; ++d) { | ||||
|       vi->push(); | ||||
|       add_vi[d] = delta; | ||||
|       vi->oplus(add_vi); | ||||
|       computeError(); | ||||
|       errorBak = _error; | ||||
|       vi->pop(); | ||||
|       vi->push(); | ||||
|       add_vi[d] = -delta; | ||||
|       vi->oplus(add_vi); | ||||
|       computeError(); | ||||
|       errorBak -= _error; | ||||
|       vi->pop(); | ||||
|       add_vi[d] = 0.0; | ||||
| 
 | ||||
|       _jacobianOplusXi.col(d) = scalar * errorBak; | ||||
|     } // end dimension
 | ||||
|   } | ||||
| 
 | ||||
|   if (jNotFixed) { | ||||
|     //Xj - estimate the jacobian numerically
 | ||||
|     double add_vj[VertexXjType::Dimension]; | ||||
|     std::fill(add_vj, add_vj + VertexXjType::Dimension, 0.0); | ||||
|     // add small step along the unit vector in each dimension
 | ||||
|     for (int d = 0; d < VertexXjType::Dimension; ++d) { | ||||
|       vj->push(); | ||||
|       add_vj[d] = delta; | ||||
|       vj->oplus(add_vj); | ||||
|       computeError(); | ||||
|       errorBak = _error; | ||||
|       vj->pop(); | ||||
|       vj->push(); | ||||
|       add_vj[d] = -delta; | ||||
|       vj->oplus(add_vj); | ||||
|       computeError(); | ||||
|       errorBak -= _error; | ||||
|       vj->pop(); | ||||
|       add_vj[d] = 0.0; | ||||
| 
 | ||||
|       _jacobianOplusXj.col(d) = scalar * errorBak; | ||||
|     } | ||||
|   } // end dimension
 | ||||
| 
 | ||||
|   _error = errorBeforeNumeric; | ||||
| #ifdef G2O_OPENMP | ||||
|   vj->unlockQuadraticForm(); | ||||
|   vi->unlockQuadraticForm(); | ||||
| #endif | ||||
| } | ||||
| 
 | ||||
| template <int D, typename E, typename VertexXiType, typename VertexXjType> | ||||
| void BaseBinaryEdge<D, E, VertexXiType, VertexXjType>::mapHessianMemory(double* d, int i, int j, bool rowMajor) | ||||
| { | ||||
|   (void) i; (void) j; | ||||
|   //assert(i == 0 && j == 1);
 | ||||
|   if (rowMajor) { | ||||
|     new (&_hessianTransposed) HessianBlockTransposedType(d, VertexXjType::Dimension, VertexXiType::Dimension); | ||||
|   } else { | ||||
|     new (&_hessian) HessianBlockType(d, VertexXiType::Dimension, VertexXjType::Dimension); | ||||
|   } | ||||
|   _hessianRowMajor = rowMajor; | ||||
| } | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
							
								
								
									
										110
									
								
								SLAM/Thirdparty/g2o/g2o/core/base_edge.h
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										110
									
								
								SLAM/Thirdparty/g2o/g2o/core/base_edge.h
									
									
									
									
										vendored
									
									
								
							| @ -1,110 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 R. Kuemmerle, G. Grisetti, H. Strasdat, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| #ifndef G2O_BASE_EDGE_H | ||||
| #define G2O_BASE_EDGE_H | ||||
| 
 | ||||
| #include <iostream> | ||||
| #include <limits> | ||||
| 
 | ||||
| #include <Eigen/Core> | ||||
| 
 | ||||
| #include "optimizable_graph.h" | ||||
| 
 | ||||
| namespace g2o { | ||||
| 
 | ||||
|   using namespace Eigen; | ||||
| 
 | ||||
|   template <int D, typename E> | ||||
|   class BaseEdge : public OptimizableGraph::Edge | ||||
|   { | ||||
|     public: | ||||
| 
 | ||||
|       static const int Dimension = D; | ||||
|       typedef E Measurement; | ||||
|       typedef Matrix<double, D, 1> ErrorVector; | ||||
|       typedef Matrix<double, D, D> InformationType; | ||||
| 
 | ||||
|       BaseEdge() : OptimizableGraph::Edge() | ||||
|       { | ||||
|         _dimension = D; | ||||
|       } | ||||
| 
 | ||||
|       virtual ~BaseEdge() {} | ||||
| 
 | ||||
|       virtual double chi2() const  | ||||
|       { | ||||
|         return _error.dot(information()*_error); | ||||
|       } | ||||
| 
 | ||||
|       virtual const double* errorData() const { return _error.data();} | ||||
|       virtual double* errorData() { return _error.data();} | ||||
|       const ErrorVector& error() const { return _error;} | ||||
|       ErrorVector& error() { return _error;} | ||||
| 
 | ||||
|       //! information matrix of the constraint
 | ||||
|       const InformationType& information() const { return _information;} | ||||
|       InformationType& information() { return _information;} | ||||
|       void setInformation(const InformationType& information) { _information = information;} | ||||
| 
 | ||||
|       virtual const double* informationData() const { return _information.data();} | ||||
|       virtual double* informationData() { return _information.data();} | ||||
| 
 | ||||
|       //! accessor functions for the measurement represented by the edge
 | ||||
|       const Measurement& measurement() const { return _measurement;} | ||||
|       virtual void setMeasurement(const Measurement& m) { _measurement = m;} | ||||
| 
 | ||||
|       virtual int rank() const {return _dimension;} | ||||
| 
 | ||||
|       virtual void initialEstimate(const OptimizableGraph::VertexSet&, OptimizableGraph::Vertex*) | ||||
|       { | ||||
|         std::cerr << "inititialEstimate() is not implemented, please give implementation in your derived class" << std::endl; | ||||
|       } | ||||
| 
 | ||||
|     protected: | ||||
| 
 | ||||
|       Measurement _measurement; | ||||
|       InformationType _information; | ||||
|       ErrorVector _error; | ||||
| 
 | ||||
|       /**
 | ||||
|        * calculate the robust information matrix by updating the information matrix of the error | ||||
|        */ | ||||
|       InformationType robustInformation(const Eigen::Vector3d& rho) | ||||
|       { | ||||
|         InformationType result = rho[1] * _information; | ||||
|         //ErrorVector weightedErrror = _information * _error;
 | ||||
|         //result.noalias() += 2 * rho[2] * (weightedErrror * weightedErrror.transpose());
 | ||||
|         return result; | ||||
|       } | ||||
| 
 | ||||
|     public: | ||||
|       EIGEN_MAKE_ALIGNED_OPERATOR_NEW | ||||
|   }; | ||||
| 
 | ||||
| } // end namespace g2o
 | ||||
| 
 | ||||
| #endif | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
							
								
								
									
										113
									
								
								SLAM/Thirdparty/g2o/g2o/core/base_multi_edge.h
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										113
									
								
								SLAM/Thirdparty/g2o/g2o/core/base_multi_edge.h
									
									
									
									
										vendored
									
									
								
							| @ -1,113 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 R. Kuemmerle, G. Grisetti, H. Strasdat, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| #ifndef G2O_BASE_MULTI_EDGE_H | ||||
| #define G2O_BASE_MULTI_EDGE_H | ||||
| 
 | ||||
| #include <iostream> | ||||
| #include <iomanip> | ||||
| #include <limits> | ||||
| 
 | ||||
| #include <Eigen/StdVector> | ||||
| 
 | ||||
| #include "base_edge.h" | ||||
| #include "robust_kernel.h" | ||||
| #include "../../config.h" | ||||
| 
 | ||||
| namespace g2o { | ||||
| 
 | ||||
|   using namespace Eigen; | ||||
| 
 | ||||
|   /**
 | ||||
|    * \brief base class to represent an edge connecting an arbitrary number of nodes | ||||
|    * | ||||
|    * D - Dimension of the measurement | ||||
|    * E - type to represent the measurement | ||||
|    */ | ||||
|   template <int D, typename E> | ||||
|   class BaseMultiEdge : public BaseEdge<D,E> | ||||
|   { | ||||
|     public: | ||||
|       /**
 | ||||
|        * \brief helper for mapping the Hessian memory of the upper triangular block | ||||
|        */ | ||||
|       struct HessianHelper { | ||||
|         Eigen::Map<MatrixXd> matrix;     ///< the mapped memory
 | ||||
|         bool transposed;          ///< the block has to be transposed
 | ||||
|         HessianHelper() : matrix(0, 0, 0), transposed(false) {} | ||||
|       }; | ||||
| 
 | ||||
|     public: | ||||
|       static const int Dimension = BaseEdge<D,E>::Dimension; | ||||
|       typedef typename BaseEdge<D,E>::Measurement Measurement; | ||||
|       typedef MatrixXd::MapType JacobianType; | ||||
|       typedef typename BaseEdge<D,E>::ErrorVector ErrorVector; | ||||
|       typedef typename BaseEdge<D,E>::InformationType InformationType; | ||||
|       typedef Eigen::Map<MatrixXd, MatrixXd::Flags & AlignedBit ? Aligned : Unaligned > HessianBlockType; | ||||
| 
 | ||||
|       BaseMultiEdge() : BaseEdge<D,E>() | ||||
|       { | ||||
|       } | ||||
|        | ||||
|       virtual void linearizeOplus(JacobianWorkspace& jacobianWorkspace); | ||||
| 
 | ||||
|       /**
 | ||||
|        * Linearizes the oplus operator in the vertex, and stores | ||||
|        * the result in temporary variable vector _jacobianOplus | ||||
|        */ | ||||
|       virtual void linearizeOplus(); | ||||
|        | ||||
|       virtual void resize(size_t size); | ||||
| 
 | ||||
|       virtual bool allVerticesFixed() const; | ||||
| 
 | ||||
|       virtual void constructQuadraticForm() ; | ||||
| 
 | ||||
|       virtual void mapHessianMemory(double* d, int i, int j, bool rowMajor); | ||||
| 
 | ||||
|       using BaseEdge<D,E>::computeError; | ||||
| 
 | ||||
|     protected: | ||||
|       using BaseEdge<D,E>::_measurement; | ||||
|       using BaseEdge<D,E>::_information; | ||||
|       using BaseEdge<D,E>::_error; | ||||
|       using BaseEdge<D,E>::_vertices; | ||||
|       using BaseEdge<D,E>::_dimension; | ||||
| 
 | ||||
|       std::vector<HessianHelper> _hessian; | ||||
|       std::vector<JacobianType, aligned_allocator<JacobianType> > _jacobianOplus; ///< jacobians of the edge (w.r.t. oplus)
 | ||||
| 
 | ||||
|       void computeQuadraticForm(const InformationType& omega, const ErrorVector& weightedError); | ||||
| 
 | ||||
|     public: | ||||
|       EIGEN_MAKE_ALIGNED_OPERATOR_NEW | ||||
|   }; | ||||
| 
 | ||||
| #include "base_multi_edge.hpp" | ||||
| 
 | ||||
| } // end namespace g2o
 | ||||
| 
 | ||||
| #endif | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
							
								
								
									
										222
									
								
								SLAM/Thirdparty/g2o/g2o/core/base_multi_edge.hpp
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										222
									
								
								SLAM/Thirdparty/g2o/g2o/core/base_multi_edge.hpp
									
									
									
									
										vendored
									
									
								
							| @ -1,222 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 R. Kuemmerle, G. Grisetti, H. Strasdat, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| namespace internal { | ||||
|   inline int computeUpperTriangleIndex(int i, int j) | ||||
|   { | ||||
|     int elemsUpToCol = ((j-1) * j) / 2; | ||||
|     return elemsUpToCol + i; | ||||
|   } | ||||
| } | ||||
| 
 | ||||
| template <int D, typename E> | ||||
| void BaseMultiEdge<D, E>::constructQuadraticForm() | ||||
| { | ||||
|   if (this->robustKernel()) { | ||||
|     double error = this->chi2(); | ||||
|     Eigen::Vector3d rho; | ||||
|     this->robustKernel()->robustify(error, rho); | ||||
|     Matrix<double, D, 1> omega_r = - _information * _error; | ||||
|     omega_r *= rho[1]; | ||||
|     computeQuadraticForm(this->robustInformation(rho), omega_r); | ||||
|   } else { | ||||
|     computeQuadraticForm(_information, - _information * _error); | ||||
|   } | ||||
| } | ||||
| 
 | ||||
| 
 | ||||
| template <int D, typename E> | ||||
| void BaseMultiEdge<D, E>::linearizeOplus(JacobianWorkspace& jacobianWorkspace) | ||||
| { | ||||
|   for (size_t i = 0; i < _vertices.size(); ++i) { | ||||
|     OptimizableGraph::Vertex* v = static_cast<OptimizableGraph::Vertex*>(_vertices[i]); | ||||
|     assert(v->dimension() >= 0); | ||||
|     new (&_jacobianOplus[i]) JacobianType(jacobianWorkspace.workspaceForVertex(i), D, v->dimension()); | ||||
|   } | ||||
|   linearizeOplus(); | ||||
| } | ||||
| 
 | ||||
| template <int D, typename E> | ||||
| void BaseMultiEdge<D, E>::linearizeOplus() | ||||
| { | ||||
| #ifdef G2O_OPENMP | ||||
|   for (size_t i = 0; i < _vertices.size(); ++i) { | ||||
|     OptimizableGraph::Vertex* v = static_cast<OptimizableGraph::Vertex*>(_vertices[i]); | ||||
|     v->lockQuadraticForm(); | ||||
|   } | ||||
| #endif | ||||
| 
 | ||||
|   const double delta = 1e-9; | ||||
|   const double scalar = 1.0 / (2*delta); | ||||
|   ErrorVector errorBak; | ||||
|   ErrorVector errorBeforeNumeric = _error; | ||||
| 
 | ||||
|   for (size_t i = 0; i < _vertices.size(); ++i) { | ||||
|     //Xi - estimate the jacobian numerically
 | ||||
|     OptimizableGraph::Vertex* vi = static_cast<OptimizableGraph::Vertex*>(_vertices[i]); | ||||
| 
 | ||||
|     if (vi->fixed()) | ||||
|       continue; | ||||
| 
 | ||||
|     const int vi_dim = vi->dimension(); | ||||
|     assert(vi_dim >= 0); | ||||
| #ifdef _MSC_VER | ||||
|     double* add_vi = new double[vi_dim]; | ||||
| #else | ||||
|     double add_vi[vi_dim]; | ||||
| #endif | ||||
|     std::fill(add_vi, add_vi + vi_dim, 0.0); | ||||
|     assert(_dimension >= 0); | ||||
|     assert(_jacobianOplus[i].rows() == _dimension && _jacobianOplus[i].cols() == vi_dim && "jacobian cache dimension does not match"); | ||||
|       _jacobianOplus[i].resize(_dimension, vi_dim); | ||||
|     // add small step along the unit vector in each dimension
 | ||||
|     for (int d = 0; d < vi_dim; ++d) { | ||||
|       vi->push(); | ||||
|       add_vi[d] = delta; | ||||
|       vi->oplus(add_vi); | ||||
|       computeError(); | ||||
|       errorBak = _error; | ||||
|       vi->pop(); | ||||
|       vi->push(); | ||||
|       add_vi[d] = -delta; | ||||
|       vi->oplus(add_vi); | ||||
|       computeError(); | ||||
|       errorBak -= _error; | ||||
|       vi->pop(); | ||||
|       add_vi[d] = 0.0; | ||||
| 
 | ||||
|       _jacobianOplus[i].col(d) = scalar * errorBak; | ||||
|     } // end dimension
 | ||||
| #ifdef _MSC_VER | ||||
|     delete[] add_vi; | ||||
| #endif | ||||
|   } | ||||
|   _error = errorBeforeNumeric; | ||||
| 
 | ||||
| #ifdef G2O_OPENMP | ||||
|   for (int i = (int)(_vertices.size()) - 1; i >= 0; --i) { | ||||
|     OptimizableGraph::Vertex* v = static_cast<OptimizableGraph::Vertex*>(_vertices[i]); | ||||
|     v->unlockQuadraticForm(); | ||||
|   } | ||||
| #endif | ||||
| 
 | ||||
| } | ||||
| 
 | ||||
| template <int D, typename E> | ||||
| void BaseMultiEdge<D, E>::mapHessianMemory(double* d, int i, int j, bool rowMajor) | ||||
| { | ||||
|   int idx = internal::computeUpperTriangleIndex(i, j); | ||||
|   assert(idx < (int)_hessian.size()); | ||||
|   OptimizableGraph::Vertex* vi = static_cast<OptimizableGraph::Vertex*>(HyperGraph::Edge::vertex(i)); | ||||
|   OptimizableGraph::Vertex* vj = static_cast<OptimizableGraph::Vertex*>(HyperGraph::Edge::vertex(j)); | ||||
|   assert(vi->dimension() >= 0); | ||||
|   assert(vj->dimension() >= 0); | ||||
|   HessianHelper& h = _hessian[idx]; | ||||
|   if (rowMajor) { | ||||
|     if (h.matrix.data() != d || h.transposed != rowMajor) | ||||
|       new (&h.matrix) HessianBlockType(d, vj->dimension(), vi->dimension()); | ||||
|   } else { | ||||
|     if (h.matrix.data() != d || h.transposed != rowMajor) | ||||
|       new (&h.matrix) HessianBlockType(d, vi->dimension(), vj->dimension()); | ||||
|   } | ||||
|   h.transposed = rowMajor; | ||||
| } | ||||
| 
 | ||||
| template <int D, typename E> | ||||
| void BaseMultiEdge<D, E>::resize(size_t size) | ||||
| { | ||||
|   BaseEdge<D,E>::resize(size); | ||||
|   int n = (int)_vertices.size(); | ||||
|   int maxIdx = (n * (n-1))/2; | ||||
|   assert(maxIdx >= 0); | ||||
|   _hessian.resize(maxIdx); | ||||
|   _jacobianOplus.resize(size, JacobianType(0,0,0)); | ||||
| } | ||||
| 
 | ||||
| template <int D, typename E> | ||||
| bool BaseMultiEdge<D, E>::allVerticesFixed() const | ||||
| { | ||||
|   for (size_t i = 0; i < _vertices.size(); ++i) { | ||||
|     if (!static_cast<const OptimizableGraph::Vertex*> (_vertices[i])->fixed()) { | ||||
|       return false; | ||||
|     } | ||||
|   } | ||||
|   return true; | ||||
| } | ||||
| 
 | ||||
| template <int D, typename E> | ||||
| void BaseMultiEdge<D, E>::computeQuadraticForm(const InformationType& omega, const ErrorVector& weightedError) | ||||
| { | ||||
|   for (size_t i = 0; i < _vertices.size(); ++i) { | ||||
|     OptimizableGraph::Vertex* from = static_cast<OptimizableGraph::Vertex*>(_vertices[i]); | ||||
|     bool istatus = !(from->fixed()); | ||||
| 
 | ||||
|     if (istatus) { | ||||
|       const MatrixXd& A = _jacobianOplus[i]; | ||||
| 
 | ||||
|       MatrixXd AtO = A.transpose() * omega; | ||||
|       int fromDim = from->dimension(); | ||||
|       assert(fromDim >= 0); | ||||
|       Eigen::Map<MatrixXd> fromMap(from->hessianData(), fromDim, fromDim); | ||||
|       Eigen::Map<VectorXd> fromB(from->bData(), fromDim); | ||||
| 
 | ||||
|       // ii block in the hessian
 | ||||
| #ifdef G2O_OPENMP | ||||
|       from->lockQuadraticForm(); | ||||
| #endif | ||||
|       fromMap.noalias() += AtO * A; | ||||
|       fromB.noalias() += A.transpose() * weightedError; | ||||
| 
 | ||||
|       // compute the off-diagonal blocks ij for all j
 | ||||
|       for (size_t j = i+1; j < _vertices.size(); ++j) { | ||||
|         OptimizableGraph::Vertex* to = static_cast<OptimizableGraph::Vertex*>(_vertices[j]); | ||||
| #ifdef G2O_OPENMP | ||||
|         to->lockQuadraticForm(); | ||||
| #endif | ||||
|         bool jstatus = !(to->fixed()); | ||||
|         if (jstatus) { | ||||
|           const MatrixXd& B = _jacobianOplus[j]; | ||||
|           int idx = internal::computeUpperTriangleIndex(i, j); | ||||
|           assert(idx < (int)_hessian.size()); | ||||
|           HessianHelper& hhelper = _hessian[idx]; | ||||
|           if (hhelper.transposed) { // we have to write to the block as transposed
 | ||||
|             hhelper.matrix.noalias() += B.transpose() * AtO.transpose(); | ||||
|           } else { | ||||
|             hhelper.matrix.noalias() += AtO * B; | ||||
|           } | ||||
|         } | ||||
| #ifdef G2O_OPENMP | ||||
|         to->unlockQuadraticForm(); | ||||
| #endif | ||||
|       } | ||||
| 
 | ||||
| #ifdef G2O_OPENMP | ||||
|       from->unlockQuadraticForm(); | ||||
| #endif | ||||
|     } | ||||
| 
 | ||||
|   } | ||||
| } | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
							
								
								
									
										100
									
								
								SLAM/Thirdparty/g2o/g2o/core/base_unary_edge.h
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										100
									
								
								SLAM/Thirdparty/g2o/g2o/core/base_unary_edge.h
									
									
									
									
										vendored
									
									
								
							| @ -1,100 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 R. Kuemmerle, G. Grisetti, H. Strasdat, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| #ifndef G2O_BASE_UNARY_EDGE_H | ||||
| #define G2O_BASE_UNARY_EDGE_H | ||||
| 
 | ||||
| #include <iostream> | ||||
| #include <cassert> | ||||
| #include <limits> | ||||
| 
 | ||||
| #include "base_edge.h" | ||||
| #include "robust_kernel.h" | ||||
| #include "../../config.h" | ||||
| 
 | ||||
| namespace g2o { | ||||
| 
 | ||||
|   using namespace Eigen; | ||||
| 
 | ||||
|   template <int D, typename E, typename VertexXi> | ||||
|   class BaseUnaryEdge : public BaseEdge<D,E> | ||||
|   { | ||||
|     public: | ||||
|       static const int Dimension = BaseEdge<D, E>::Dimension; | ||||
|       typedef typename BaseEdge<D,E>::Measurement Measurement; | ||||
|       typedef VertexXi VertexXiType; | ||||
|       typedef typename Matrix<double, D, VertexXiType::Dimension>::AlignedMapType JacobianXiOplusType; | ||||
|       typedef typename BaseEdge<D,E>::ErrorVector ErrorVector; | ||||
|       typedef typename BaseEdge<D,E>::InformationType InformationType; | ||||
| 
 | ||||
|       BaseUnaryEdge() : BaseEdge<D,E>(), | ||||
|         _jacobianOplusXi(0, D, VertexXiType::Dimension) | ||||
|       { | ||||
|         _vertices.resize(1); | ||||
|       } | ||||
| 
 | ||||
|       virtual void resize(size_t size); | ||||
| 
 | ||||
|       virtual bool allVerticesFixed() const; | ||||
| 
 | ||||
|       virtual void linearizeOplus(JacobianWorkspace& jacobianWorkspace); | ||||
| 
 | ||||
|       /**
 | ||||
|        * Linearizes the oplus operator in the vertex, and stores | ||||
|        * the result in temporary variables _jacobianOplusXi and _jacobianOplusXj | ||||
|        */ | ||||
|       virtual void linearizeOplus(); | ||||
| 
 | ||||
|       //! returns the result of the linearization in the manifold space for the node xi
 | ||||
|       const JacobianXiOplusType& jacobianOplusXi() const { return _jacobianOplusXi;} | ||||
| 
 | ||||
|       virtual void constructQuadraticForm(); | ||||
| 
 | ||||
|       virtual void initialEstimate(const OptimizableGraph::VertexSet& from, OptimizableGraph::Vertex* to); | ||||
| 
 | ||||
|       virtual void mapHessianMemory(double*, int, int, bool) {assert(0 && "BaseUnaryEdge does not map memory of the Hessian");} | ||||
| 
 | ||||
|       using BaseEdge<D,E>::resize; | ||||
|       using BaseEdge<D,E>::computeError; | ||||
| 
 | ||||
|     protected: | ||||
|       using BaseEdge<D,E>::_measurement; | ||||
|       using BaseEdge<D,E>::_information; | ||||
|       using BaseEdge<D,E>::_error; | ||||
|       using BaseEdge<D,E>::_vertices; | ||||
|       using BaseEdge<D,E>::_dimension; | ||||
| 
 | ||||
|       JacobianXiOplusType _jacobianOplusXi; | ||||
| 
 | ||||
|     public: | ||||
|       EIGEN_MAKE_ALIGNED_OPERATOR_NEW | ||||
|   }; | ||||
| 
 | ||||
| #include "base_unary_edge.hpp" | ||||
| 
 | ||||
| } // end namespace g2o
 | ||||
| 
 | ||||
| #endif | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
							
								
								
									
										129
									
								
								SLAM/Thirdparty/g2o/g2o/core/base_unary_edge.hpp
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										129
									
								
								SLAM/Thirdparty/g2o/g2o/core/base_unary_edge.hpp
									
									
									
									
										vendored
									
									
								
							| @ -1,129 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 R. Kuemmerle, G. Grisetti, H. Strasdat, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| template <int D, typename E, typename VertexXiType> | ||||
| void BaseUnaryEdge<D, E, VertexXiType>::resize(size_t size) | ||||
| { | ||||
|   if (size != 1) { | ||||
|     std::cerr << "WARNING, attempting to resize unary edge " << BaseEdge<D, E>::id() << " to " << size << std::endl; | ||||
|   } | ||||
|   BaseEdge<D, E>::resize(size); | ||||
| } | ||||
| 
 | ||||
| template <int D, typename E, typename VertexXiType> | ||||
| bool BaseUnaryEdge<D, E, VertexXiType>::allVerticesFixed() const | ||||
| { | ||||
|   return static_cast<const VertexXiType*> (_vertices[0])->fixed(); | ||||
| } | ||||
| 
 | ||||
| template <int D, typename E, typename VertexXiType> | ||||
| void BaseUnaryEdge<D, E, VertexXiType>::constructQuadraticForm() | ||||
| { | ||||
|   VertexXiType* from=static_cast<VertexXiType*>(_vertices[0]); | ||||
| 
 | ||||
|   // chain rule to get the Jacobian of the nodes in the manifold domain
 | ||||
|   const JacobianXiOplusType& A = jacobianOplusXi(); | ||||
|   const InformationType& omega = _information; | ||||
| 
 | ||||
|   bool istatus = !from->fixed(); | ||||
|   if (istatus) { | ||||
| #ifdef G2O_OPENMP | ||||
|     from->lockQuadraticForm(); | ||||
| #endif | ||||
|     if (this->robustKernel()) { | ||||
|       double error = this->chi2(); | ||||
|       Eigen::Vector3d rho; | ||||
|       this->robustKernel()->robustify(error, rho); | ||||
|       InformationType weightedOmega = this->robustInformation(rho); | ||||
| 
 | ||||
|       from->b().noalias() -= rho[1] * A.transpose() * omega * _error; | ||||
|       from->A().noalias() += A.transpose() * weightedOmega * A; | ||||
|     } else { | ||||
|       from->b().noalias() -= A.transpose() * omega * _error; | ||||
|       from->A().noalias() += A.transpose() * omega * A; | ||||
|     } | ||||
| #ifdef G2O_OPENMP | ||||
|     from->unlockQuadraticForm(); | ||||
| #endif | ||||
|   } | ||||
| } | ||||
| 
 | ||||
| template <int D, typename E, typename VertexXiType> | ||||
| void BaseUnaryEdge<D, E, VertexXiType>::linearizeOplus(JacobianWorkspace& jacobianWorkspace) | ||||
| { | ||||
|   new (&_jacobianOplusXi) JacobianXiOplusType(jacobianWorkspace.workspaceForVertex(0), D, VertexXiType::Dimension); | ||||
|   linearizeOplus(); | ||||
| } | ||||
| 
 | ||||
| template <int D, typename E, typename VertexXiType> | ||||
| void BaseUnaryEdge<D, E, VertexXiType>::linearizeOplus() | ||||
| { | ||||
|   //Xi - estimate the jacobian numerically
 | ||||
|   VertexXiType* vi = static_cast<VertexXiType*>(_vertices[0]); | ||||
| 
 | ||||
|   if (vi->fixed()) | ||||
|     return; | ||||
| 
 | ||||
| #ifdef G2O_OPENMP | ||||
|   vi->lockQuadraticForm(); | ||||
| #endif | ||||
| 
 | ||||
|   const double delta = 1e-9; | ||||
|   const double scalar = 1.0 / (2*delta); | ||||
|   ErrorVector error1; | ||||
|   ErrorVector errorBeforeNumeric = _error; | ||||
| 
 | ||||
|   double add_vi[VertexXiType::Dimension]; | ||||
|   std::fill(add_vi, add_vi + VertexXiType::Dimension, 0.0); | ||||
|   // add small step along the unit vector in each dimension
 | ||||
|   for (int d = 0; d < VertexXiType::Dimension; ++d) { | ||||
|     vi->push(); | ||||
|     add_vi[d] = delta; | ||||
|     vi->oplus(add_vi); | ||||
|     computeError(); | ||||
|     error1 = _error; | ||||
|     vi->pop(); | ||||
|     vi->push(); | ||||
|     add_vi[d] = -delta; | ||||
|     vi->oplus(add_vi); | ||||
|     computeError(); | ||||
|     vi->pop(); | ||||
|     add_vi[d] = 0.0; | ||||
| 
 | ||||
|     _jacobianOplusXi.col(d) = scalar * (error1 - _error); | ||||
|   } // end dimension
 | ||||
| 
 | ||||
|   _error = errorBeforeNumeric; | ||||
| #ifdef G2O_OPENMP | ||||
|   vi->unlockQuadraticForm(); | ||||
| #endif | ||||
| } | ||||
| 
 | ||||
| template <int D, typename E, typename VertexXiType> | ||||
| void BaseUnaryEdge<D, E, VertexXiType>::initialEstimate(const OptimizableGraph::VertexSet&, OptimizableGraph::Vertex*) | ||||
| { | ||||
|   std::cerr << __PRETTY_FUNCTION__ << " is not implemented, please give implementation in your derived class" << std::endl; | ||||
| } | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
							
								
								
									
										120
									
								
								SLAM/Thirdparty/g2o/g2o/core/base_vertex.h
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										120
									
								
								SLAM/Thirdparty/g2o/g2o/core/base_vertex.h
									
									
									
									
										vendored
									
									
								
							| @ -1,120 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 R. Kuemmerle, G. Grisetti, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| #ifndef G2O_BASE_VERTEX_H | ||||
| #define G2O_BASE_VERTEX_H | ||||
| 
 | ||||
| #include "optimizable_graph.h" | ||||
| #include "creators.h" | ||||
| #include "../stuff/macros.h" | ||||
| 
 | ||||
| #include <Eigen/Core> | ||||
| #include <Eigen/Dense> | ||||
| #include <Eigen/Cholesky> | ||||
| #include <Eigen/StdVector> | ||||
| #include <stack> | ||||
| 
 | ||||
| namespace g2o { | ||||
| 
 | ||||
|   using namespace Eigen; | ||||
| 
 | ||||
| 
 | ||||
| /**
 | ||||
|  * \brief Templatized BaseVertex | ||||
|  * | ||||
|  * Templatized BaseVertex | ||||
|  * D  : minimal dimension of the vertex, e.g., 3 for rotation in 3D | ||||
|  * T  : internal type to represent the estimate, e.g., Quaternion for rotation in 3D | ||||
|  */ | ||||
|   template <int D, typename T> | ||||
|   class BaseVertex : public OptimizableGraph::Vertex { | ||||
|     public: | ||||
|     typedef T EstimateType; | ||||
|     typedef std::stack<EstimateType,  | ||||
|                        std::vector<EstimateType,  Eigen::aligned_allocator<EstimateType> > > | ||||
|     BackupStackType; | ||||
| 
 | ||||
|     static const int Dimension = D;           ///< dimension of the estimate (minimal) in the manifold space
 | ||||
| 
 | ||||
|     typedef Eigen::Map<Matrix<double, D, D>, Matrix<double,D,D>::Flags & AlignedBit ? Aligned : Unaligned >  HessianBlockType; | ||||
| 
 | ||||
|   public: | ||||
|     BaseVertex(); | ||||
| 
 | ||||
|     virtual const double& hessian(int i, int j) const { assert(i<D && j<D); return _hessian(i,j);} | ||||
|     virtual double& hessian(int i, int j)  { assert(i<D && j<D); return _hessian(i,j);} | ||||
|     virtual double hessianDeterminant() const {return _hessian.determinant();} | ||||
|     virtual double* hessianData() { return const_cast<double*>(_hessian.data());} | ||||
| 
 | ||||
|     virtual void mapHessianMemory(double* d); | ||||
| 
 | ||||
|     virtual int copyB(double* b_) const { | ||||
|       memcpy(b_, _b.data(), Dimension * sizeof(double)); | ||||
|       return Dimension;  | ||||
|     } | ||||
| 
 | ||||
|     virtual const double& b(int i) const { assert(i < D); return _b(i);} | ||||
|     virtual double& b(int i) { assert(i < D); return _b(i);} | ||||
|     virtual double* bData() { return _b.data();} | ||||
| 
 | ||||
|     virtual void clearQuadraticForm(); | ||||
| 
 | ||||
|     //! updates the current vertex with the direct solution x += H_ii\b_ii
 | ||||
|     //! @returns the determinant of the inverted hessian
 | ||||
|     virtual double solveDirect(double lambda=0); | ||||
| 
 | ||||
|     //! return right hand side b of the constructed linear system
 | ||||
|     Matrix<double, D, 1>& b() { return _b;} | ||||
|     const Matrix<double, D, 1>& b() const { return _b;} | ||||
|     //! return the hessian block associated with the vertex
 | ||||
|     HessianBlockType& A() { return _hessian;} | ||||
|     const HessianBlockType& A() const { return _hessian;} | ||||
| 
 | ||||
|     virtual void push() { _backup.push(_estimate);} | ||||
|     virtual void pop() { assert(!_backup.empty()); _estimate = _backup.top(); _backup.pop(); updateCache();} | ||||
|     virtual void discardTop() { assert(!_backup.empty()); _backup.pop();} | ||||
|     virtual int stackSize() const {return _backup.size();} | ||||
| 
 | ||||
|     //! return the current estimate of the vertex
 | ||||
|     const EstimateType& estimate() const { return _estimate;} | ||||
|     //! set the estimate for the vertex also calls updateCache()
 | ||||
|     void setEstimate(const EstimateType& et) { _estimate = et; updateCache();} | ||||
| 
 | ||||
|   protected: | ||||
|     HessianBlockType _hessian; | ||||
|     Matrix<double, D, 1> _b; | ||||
|     EstimateType _estimate; | ||||
|     BackupStackType _backup; | ||||
|   public: | ||||
|     EIGEN_MAKE_ALIGNED_OPERATOR_NEW | ||||
| }; | ||||
| 
 | ||||
| #include "base_vertex.hpp" | ||||
| 
 | ||||
| } // end namespace g2o
 | ||||
| 
 | ||||
| 
 | ||||
| #endif | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
							
								
								
									
										55
									
								
								SLAM/Thirdparty/g2o/g2o/core/base_vertex.hpp
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										55
									
								
								SLAM/Thirdparty/g2o/g2o/core/base_vertex.hpp
									
									
									
									
										vendored
									
									
								
							| @ -1,55 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 R. Kuemmerle, G. Grisetti, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| template <int D, typename T> | ||||
| BaseVertex<D, T>::BaseVertex() : | ||||
|   OptimizableGraph::Vertex(), | ||||
|   _hessian(0, D, D) | ||||
| { | ||||
|   _dimension = D; | ||||
| } | ||||
| 
 | ||||
| template <int D, typename T> | ||||
| double BaseVertex<D, T>::solveDirect(double lambda) { | ||||
|   Matrix <double, D, D> tempA=_hessian + Matrix <double, D, D>::Identity()*lambda; | ||||
|   double det=tempA.determinant(); | ||||
|   if (g2o_isnan(det) || det < std::numeric_limits<double>::epsilon()) | ||||
|     return det; | ||||
|   Matrix <double, D, 1> dx=tempA.llt().solve(_b); | ||||
|   oplus(&dx[0]); | ||||
|   return det; | ||||
| } | ||||
| 
 | ||||
| template <int D, typename T> | ||||
| void BaseVertex<D, T>::clearQuadraticForm() { | ||||
|   _b.setZero(); | ||||
| } | ||||
| 
 | ||||
| template <int D, typename T> | ||||
| void BaseVertex<D, T>::mapHessianMemory(double* d) | ||||
| { | ||||
|   new (&_hessian) HessianBlockType(d, D, D); | ||||
| } | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
							
								
								
									
										90
									
								
								SLAM/Thirdparty/g2o/g2o/core/batch_stats.cpp
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										90
									
								
								SLAM/Thirdparty/g2o/g2o/core/batch_stats.cpp
									
									
									
									
										vendored
									
									
								
							| @ -1,90 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 R. Kuemmerle, G. Grisetti, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| #include "batch_stats.h" | ||||
| #include <cstring> | ||||
| 
 | ||||
| namespace g2o { | ||||
|   using namespace std; | ||||
| 
 | ||||
|   G2OBatchStatistics* G2OBatchStatistics::_globalStats=0; | ||||
| 
 | ||||
|   #ifndef PTHING | ||||
|   #define PTHING(s) \ | ||||
|     #s << "= " << (st.s) << "\t " | ||||
|   #endif | ||||
| 
 | ||||
|   G2OBatchStatistics::G2OBatchStatistics(){ | ||||
|     // zero all.
 | ||||
|     memset (this, 0, sizeof(G2OBatchStatistics)); | ||||
| 
 | ||||
|     // set the iteration to -1 to show that it isn't valid
 | ||||
|     iteration = -1; | ||||
|   } | ||||
| 
 | ||||
|   std::ostream& operator << (std::ostream& os , const G2OBatchStatistics& st) | ||||
|   { | ||||
|     os << PTHING(iteration); | ||||
| 
 | ||||
|     os << PTHING( numVertices ); // how many vertices are involved
 | ||||
|     os << PTHING( numEdges ); // hoe many edges
 | ||||
|     os << PTHING(  chi2 );  // total chi2
 | ||||
|      | ||||
|     /** timings **/ | ||||
|     // nonlinear part
 | ||||
|     os << PTHING(  timeResiduals );   | ||||
|     os << PTHING(  timeLinearize );   // jacobians
 | ||||
|     os << PTHING(  timeQuadraticForm ); // construct the quadratic form in the graph
 | ||||
|      | ||||
|     // block_solver (constructs Ax=b, plus maybe schur);
 | ||||
|     os << PTHING(  timeSchurComplement ); // compute schur complement (0 if not done);
 | ||||
|      | ||||
|     // linear solver (computes Ax=b); );
 | ||||
|     os << PTHING(  timeSymbolicDecomposition ); // symbolic decomposition (0 if not done);
 | ||||
|     os << PTHING(  timeNumericDecomposition ); // numeric decomposition  (0 if not done);
 | ||||
|     os << PTHING(  timeLinearSolution );             // total time for solving Ax=b
 | ||||
|     os << PTHING(  iterationsLinearSolver );  // iterations of PCG
 | ||||
|     os << PTHING(  timeUpdate ); // oplus
 | ||||
|     os << PTHING(  timeIteration ); // total time );
 | ||||
| 
 | ||||
|     os << PTHING( levenbergIterations ); | ||||
|     os << PTHING( timeLinearSolver); | ||||
| 
 | ||||
|     os << PTHING(hessianDimension); | ||||
|     os << PTHING(hessianPoseDimension); | ||||
|     os << PTHING(hessianLandmarkDimension); | ||||
|     os << PTHING(choleskyNNZ); | ||||
|     os << PTHING(timeMarginals); | ||||
| 
 | ||||
|     return os; | ||||
|   }; | ||||
| 
 | ||||
|   void G2OBatchStatistics::setGlobalStats(G2OBatchStatistics* b) | ||||
|   { | ||||
|     _globalStats = b; | ||||
|   } | ||||
| 
 | ||||
| } // end namespace
 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
							
								
								
									
										83
									
								
								SLAM/Thirdparty/g2o/g2o/core/batch_stats.h
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										83
									
								
								SLAM/Thirdparty/g2o/g2o/core/batch_stats.h
									
									
									
									
										vendored
									
									
								
							| @ -1,83 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 R. Kuemmerle, G. Grisetti, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| #ifndef G2O_BATCH_STATS_H_ | ||||
| #define G2O_BATCH_STATS_H_ | ||||
| 
 | ||||
| #include <iostream> | ||||
| #include <vector> | ||||
| 
 | ||||
| 
 | ||||
| namespace g2o { | ||||
| 
 | ||||
|   /**
 | ||||
|    * \brief statistics about the optimization | ||||
|    */ | ||||
|   struct  G2OBatchStatistics { | ||||
|     G2OBatchStatistics(); | ||||
|     int iteration;                    ///< which iteration
 | ||||
|     int numVertices;                  ///< how many vertices are involved
 | ||||
|     int numEdges;                     ///< how many edges
 | ||||
|     double chi2;                      ///< total chi2
 | ||||
| 
 | ||||
|     /** timings **/ | ||||
|     // nonlinear part
 | ||||
|     double timeResiduals;             ///< residuals
 | ||||
|     double timeLinearize;             ///< jacobians
 | ||||
|     double timeQuadraticForm;         ///< construct the quadratic form in the graph
 | ||||
|     int levenbergIterations;          ///< number of iterations performed by LM
 | ||||
|     // block_solver (constructs Ax=b, plus maybe schur)
 | ||||
|     double timeSchurComplement;      ///< compute schur complement (0 if not done)
 | ||||
| 
 | ||||
|     // linear solver (computes Ax=b);
 | ||||
|     double timeSymbolicDecomposition; ///< symbolic decomposition (0 if not done)
 | ||||
|     double timeNumericDecomposition;  ///< numeric decomposition  (0 if not done)
 | ||||
|     double timeLinearSolution;        ///< total time for solving Ax=b (including detup for schur)
 | ||||
|     double timeLinearSolver;          ///< time for solving, excluding Schur setup
 | ||||
|     int    iterationsLinearSolver;    ///< iterations of PCG, (0 if not used, i.e., Cholesky)
 | ||||
|     double timeUpdate;                ///< time to apply the update
 | ||||
|     double timeIteration;             ///< total time;
 | ||||
| 
 | ||||
|     double timeMarginals;             ///< computing the inverse elements (solve blocks) and thus the marginal covariances
 | ||||
| 
 | ||||
|     // information about the Hessian matrix
 | ||||
|     size_t hessianDimension;          ///< rows / cols of the Hessian
 | ||||
|     size_t hessianPoseDimension;      ///< dimension of the pose matrix in Schur
 | ||||
|     size_t hessianLandmarkDimension;  ///< dimension of the landmark matrix in Schur
 | ||||
|     size_t choleskyNNZ;               ///< number of non-zeros in the cholesky factor
 | ||||
| 
 | ||||
|     static G2OBatchStatistics* globalStats() {return _globalStats;} | ||||
|     static void setGlobalStats(G2OBatchStatistics* b); | ||||
|     protected: | ||||
|     static G2OBatchStatistics* _globalStats; | ||||
|   }; | ||||
| 
 | ||||
|    std::ostream& operator<<(std::ostream&, const G2OBatchStatistics&); | ||||
| 
 | ||||
|   typedef std::vector<G2OBatchStatistics> BatchStatisticsContainer; | ||||
| } | ||||
| 
 | ||||
| #endif | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
							
								
								
									
										193
									
								
								SLAM/Thirdparty/g2o/g2o/core/block_solver.h
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										193
									
								
								SLAM/Thirdparty/g2o/g2o/core/block_solver.h
									
									
									
									
										vendored
									
									
								
							| @ -1,193 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 R. Kuemmerle, G. Grisetti, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| #ifndef G2O_BLOCK_SOLVER_H | ||||
| #define G2O_BLOCK_SOLVER_H | ||||
| #include <Eigen/Core> | ||||
| #include "solver.h" | ||||
| #include "linear_solver.h" | ||||
| #include "sparse_block_matrix.h" | ||||
| #include "sparse_block_matrix_diagonal.h" | ||||
| #include "openmp_mutex.h" | ||||
| #include "../../config.h" | ||||
| 
 | ||||
| namespace g2o { | ||||
|   using namespace Eigen; | ||||
| 
 | ||||
|   /**
 | ||||
|    * \brief traits to summarize the properties of the fixed size optimization problem | ||||
|    */ | ||||
|   template <int _PoseDim, int _LandmarkDim> | ||||
|   struct BlockSolverTraits | ||||
|   { | ||||
|     static const int PoseDim = _PoseDim; | ||||
|     static const int LandmarkDim = _LandmarkDim; | ||||
|     typedef Matrix<double, PoseDim, PoseDim> PoseMatrixType; | ||||
|     typedef Matrix<double, LandmarkDim, LandmarkDim> LandmarkMatrixType; | ||||
|     typedef Matrix<double, PoseDim, LandmarkDim> PoseLandmarkMatrixType; | ||||
|     typedef Matrix<double, PoseDim, 1> PoseVectorType; | ||||
|     typedef Matrix<double, LandmarkDim, 1> LandmarkVectorType; | ||||
| 
 | ||||
|     typedef SparseBlockMatrix<PoseMatrixType> PoseHessianType; | ||||
|     typedef SparseBlockMatrix<LandmarkMatrixType> LandmarkHessianType; | ||||
|     typedef SparseBlockMatrix<PoseLandmarkMatrixType> PoseLandmarkHessianType; | ||||
|     typedef LinearSolver<PoseMatrixType> LinearSolverType; | ||||
|   }; | ||||
| 
 | ||||
|   /**
 | ||||
|    * \brief traits to summarize the properties of the dynamic size optimization problem | ||||
|    */ | ||||
|   template <> | ||||
|   struct BlockSolverTraits<Eigen::Dynamic, Eigen::Dynamic> | ||||
|   { | ||||
|     static const int PoseDim = Eigen::Dynamic; | ||||
|     static const int LandmarkDim = Eigen::Dynamic; | ||||
|     typedef MatrixXd PoseMatrixType; | ||||
|     typedef MatrixXd LandmarkMatrixType; | ||||
|     typedef MatrixXd PoseLandmarkMatrixType; | ||||
|     typedef VectorXd PoseVectorType; | ||||
|     typedef VectorXd LandmarkVectorType; | ||||
| 
 | ||||
|     typedef SparseBlockMatrix<PoseMatrixType> PoseHessianType; | ||||
|     typedef SparseBlockMatrix<LandmarkMatrixType> LandmarkHessianType; | ||||
|     typedef SparseBlockMatrix<PoseLandmarkMatrixType> PoseLandmarkHessianType; | ||||
|     typedef LinearSolver<PoseMatrixType> LinearSolverType; | ||||
|   }; | ||||
| 
 | ||||
|   /**
 | ||||
|    * \brief base for the block solvers with some basic function interfaces | ||||
|    */ | ||||
|   class BlockSolverBase : public Solver | ||||
|   { | ||||
|     public: | ||||
|       virtual ~BlockSolverBase() {} | ||||
|       /**
 | ||||
|        * compute dest = H * src | ||||
|        */ | ||||
|       virtual void multiplyHessian(double* dest, const double* src) const = 0; | ||||
|   }; | ||||
| 
 | ||||
|   /**
 | ||||
|    * \brief Implementation of a solver operating on the blocks of the Hessian | ||||
|    */ | ||||
|   template <typename Traits> | ||||
|   class BlockSolver: public BlockSolverBase { | ||||
|     public: | ||||
| 
 | ||||
|       static const int PoseDim = Traits::PoseDim; | ||||
|       static const int LandmarkDim = Traits::LandmarkDim; | ||||
|       typedef typename Traits::PoseMatrixType PoseMatrixType; | ||||
|       typedef typename Traits::LandmarkMatrixType LandmarkMatrixType;  | ||||
|       typedef typename Traits::PoseLandmarkMatrixType PoseLandmarkMatrixType; | ||||
|       typedef typename Traits::PoseVectorType PoseVectorType; | ||||
|       typedef typename Traits::LandmarkVectorType LandmarkVectorType; | ||||
| 
 | ||||
|       typedef typename Traits::PoseHessianType PoseHessianType; | ||||
|       typedef typename Traits::LandmarkHessianType LandmarkHessianType; | ||||
|       typedef typename Traits::PoseLandmarkHessianType PoseLandmarkHessianType; | ||||
|       typedef typename Traits::LinearSolverType LinearSolverType; | ||||
| 
 | ||||
|     public: | ||||
| 
 | ||||
|       /**
 | ||||
|        * allocate a block solver ontop of the underlying linear solver. | ||||
|        * NOTE: The BlockSolver assumes exclusive access to the linear solver and will therefore free the pointer | ||||
|        * in its destructor. | ||||
|        */ | ||||
|       BlockSolver(LinearSolverType* linearSolver); | ||||
|       ~BlockSolver(); | ||||
| 
 | ||||
|       virtual bool init(SparseOptimizer* optmizer, bool online = false); | ||||
|       virtual bool buildStructure(bool zeroBlocks = false); | ||||
|       virtual bool updateStructure(const std::vector<HyperGraph::Vertex*>& vset, const HyperGraph::EdgeSet& edges); | ||||
|       virtual bool buildSystem(); | ||||
|       virtual bool solve(); | ||||
|       virtual bool computeMarginals(SparseBlockMatrix<MatrixXd>& spinv, const std::vector<std::pair<int, int> >& blockIndices); | ||||
|       virtual bool setLambda(double lambda, bool backup = false); | ||||
|       virtual void restoreDiagonal(); | ||||
|       virtual bool supportsSchur() {return true;} | ||||
|       virtual bool schur() { return _doSchur;} | ||||
|       virtual void setSchur(bool s) { _doSchur = s;} | ||||
| 
 | ||||
|       LinearSolver<PoseMatrixType>* linearSolver() const { return _linearSolver;} | ||||
| 
 | ||||
|       virtual void setWriteDebug(bool writeDebug); | ||||
|       virtual bool writeDebug() const {return _linearSolver->writeDebug();} | ||||
| 
 | ||||
|       virtual bool saveHessian(const std::string& fileName) const; | ||||
| 
 | ||||
|       virtual void multiplyHessian(double* dest, const double* src) const { _Hpp->multiplySymmetricUpperTriangle(dest, src);} | ||||
| 
 | ||||
|     protected: | ||||
|       void resize(int* blockPoseIndices, int numPoseBlocks,  | ||||
|           int* blockLandmarkIndices, int numLandmarkBlocks, int totalDim); | ||||
| 
 | ||||
|       void deallocate(); | ||||
| 
 | ||||
|       SparseBlockMatrix<PoseMatrixType>* _Hpp; | ||||
|       SparseBlockMatrix<LandmarkMatrixType>* _Hll; | ||||
|       SparseBlockMatrix<PoseLandmarkMatrixType>* _Hpl; | ||||
| 
 | ||||
|       SparseBlockMatrix<PoseMatrixType>* _Hschur; | ||||
|       SparseBlockMatrixDiagonal<LandmarkMatrixType>* _DInvSchur; | ||||
| 
 | ||||
|       SparseBlockMatrixCCS<PoseLandmarkMatrixType>* _HplCCS; | ||||
|       SparseBlockMatrixCCS<PoseMatrixType>* _HschurTransposedCCS; | ||||
| 
 | ||||
|       LinearSolver<PoseMatrixType>* _linearSolver; | ||||
| 
 | ||||
|       std::vector<PoseVectorType, Eigen::aligned_allocator<PoseVectorType> > _diagonalBackupPose; | ||||
|       std::vector<LandmarkVectorType, Eigen::aligned_allocator<LandmarkVectorType> > _diagonalBackupLandmark; | ||||
| 
 | ||||
| #    ifdef G2O_OPENMP | ||||
|       std::vector<OpenMPMutex> _coefficientsMutex; | ||||
| #    endif | ||||
| 
 | ||||
|       bool _doSchur; | ||||
| 
 | ||||
|       double* _coefficients; | ||||
|       double* _bschur; | ||||
| 
 | ||||
|       int _numPoses, _numLandmarks; | ||||
|       int _sizePoses, _sizeLandmarks; | ||||
|   }; | ||||
| 
 | ||||
| 
 | ||||
|   //variable size solver
 | ||||
|   typedef BlockSolver< BlockSolverTraits<Eigen::Dynamic, Eigen::Dynamic> > BlockSolverX; | ||||
|   // solver for BA/3D SLAM
 | ||||
|   typedef BlockSolver< BlockSolverTraits<6, 3> > BlockSolver_6_3;   | ||||
|   // solver fo BA with scale
 | ||||
|   typedef BlockSolver< BlockSolverTraits<7, 3> > BlockSolver_7_3;   | ||||
|   // 2Dof landmarks 3Dof poses
 | ||||
|   typedef BlockSolver< BlockSolverTraits<3, 2> > BlockSolver_3_2; | ||||
| 
 | ||||
| } // end namespace
 | ||||
| 
 | ||||
| #include "block_solver.hpp" | ||||
| 
 | ||||
| 
 | ||||
| #endif | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
							
								
								
									
										634
									
								
								SLAM/Thirdparty/g2o/g2o/core/block_solver.hpp
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										634
									
								
								SLAM/Thirdparty/g2o/g2o/core/block_solver.hpp
									
									
									
									
										vendored
									
									
								
							| @ -1,634 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 R. Kuemmerle, G. Grisetti, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| #include "sparse_optimizer.h" | ||||
| #include <Eigen/LU> | ||||
| #include <fstream> | ||||
| #include <iomanip> | ||||
| 
 | ||||
| #include "../stuff/timeutil.h" | ||||
| #include "../stuff/macros.h" | ||||
| #include "../stuff/misc.h" | ||||
| 
 | ||||
| namespace g2o { | ||||
| 
 | ||||
| using namespace std; | ||||
| using namespace Eigen; | ||||
| 
 | ||||
| template <typename Traits> | ||||
| BlockSolver<Traits>::BlockSolver(LinearSolverType* linearSolver) : | ||||
|   BlockSolverBase(), | ||||
|   _linearSolver(linearSolver) | ||||
| { | ||||
|   // workspace
 | ||||
|   _Hpp=0; | ||||
|   _Hll=0; | ||||
|   _Hpl=0; | ||||
|   _HplCCS = 0; | ||||
|   _HschurTransposedCCS = 0; | ||||
|   _Hschur=0; | ||||
|   _DInvSchur=0; | ||||
|   _coefficients=0; | ||||
|   _bschur = 0; | ||||
|   _xSize=0; | ||||
|   _numPoses=0; | ||||
|   _numLandmarks=0; | ||||
|   _sizePoses=0; | ||||
|   _sizeLandmarks=0; | ||||
|   _doSchur=true; | ||||
| } | ||||
| 
 | ||||
| template <typename Traits> | ||||
| void BlockSolver<Traits>::resize(int* blockPoseIndices, int numPoseBlocks,  | ||||
|               int* blockLandmarkIndices, int numLandmarkBlocks, | ||||
|               int s) | ||||
| { | ||||
|   deallocate(); | ||||
| 
 | ||||
|   resizeVector(s); | ||||
| 
 | ||||
|   if (_doSchur) { | ||||
|     // the following two are only used in schur
 | ||||
|     assert(_sizePoses > 0 && "allocating with wrong size"); | ||||
|     _coefficients = new double [s]; | ||||
|     _bschur = new double[_sizePoses]; | ||||
|   } | ||||
| 
 | ||||
|   _Hpp=new PoseHessianType(blockPoseIndices, blockPoseIndices, numPoseBlocks, numPoseBlocks); | ||||
|   if (_doSchur) { | ||||
|     _Hschur=new PoseHessianType(blockPoseIndices, blockPoseIndices, numPoseBlocks, numPoseBlocks); | ||||
|     _Hll=new LandmarkHessianType(blockLandmarkIndices, blockLandmarkIndices, numLandmarkBlocks, numLandmarkBlocks); | ||||
|     _DInvSchur = new SparseBlockMatrixDiagonal<LandmarkMatrixType>(_Hll->colBlockIndices()); | ||||
|     _Hpl=new PoseLandmarkHessianType(blockPoseIndices, blockLandmarkIndices, numPoseBlocks, numLandmarkBlocks); | ||||
|     _HplCCS = new SparseBlockMatrixCCS<PoseLandmarkMatrixType>(_Hpl->rowBlockIndices(), _Hpl->colBlockIndices()); | ||||
|     _HschurTransposedCCS = new SparseBlockMatrixCCS<PoseMatrixType>(_Hschur->colBlockIndices(), _Hschur->rowBlockIndices()); | ||||
| #ifdef G2O_OPENMP | ||||
|     _coefficientsMutex.resize(numPoseBlocks); | ||||
| #endif | ||||
|   } | ||||
| } | ||||
| 
 | ||||
| template <typename Traits> | ||||
| void BlockSolver<Traits>::deallocate() | ||||
| { | ||||
|   if (_Hpp){ | ||||
|     delete _Hpp; | ||||
|     _Hpp=0; | ||||
|   } | ||||
|   if (_Hll){ | ||||
|     delete _Hll; | ||||
|     _Hll=0; | ||||
|   } | ||||
|   if (_Hpl){ | ||||
|     delete _Hpl; | ||||
|     _Hpl = 0; | ||||
|   } | ||||
|   if (_Hschur){ | ||||
|     delete _Hschur; | ||||
|     _Hschur=0; | ||||
|   } | ||||
|   if (_DInvSchur){ | ||||
|     delete _DInvSchur; | ||||
|     _DInvSchur=0; | ||||
|   } | ||||
|   if (_coefficients) { | ||||
|     delete[] _coefficients; | ||||
|     _coefficients = 0; | ||||
|   } | ||||
|   if (_bschur) { | ||||
|     delete[] _bschur; | ||||
|     _bschur = 0; | ||||
|   } | ||||
|   if (_HplCCS) { | ||||
|     delete _HplCCS; | ||||
|     _HplCCS = 0; | ||||
|   } | ||||
|   if (_HschurTransposedCCS) { | ||||
|     delete _HschurTransposedCCS; | ||||
|     _HschurTransposedCCS = 0; | ||||
|   } | ||||
| } | ||||
| 
 | ||||
| template <typename Traits> | ||||
| BlockSolver<Traits>::~BlockSolver() | ||||
| { | ||||
|   delete _linearSolver; | ||||
|   deallocate(); | ||||
| } | ||||
| 
 | ||||
| template <typename Traits> | ||||
| bool BlockSolver<Traits>::buildStructure(bool zeroBlocks) | ||||
| { | ||||
|   assert(_optimizer); | ||||
| 
 | ||||
|   size_t sparseDim = 0; | ||||
|   _numPoses=0; | ||||
|   _numLandmarks=0; | ||||
|   _sizePoses=0; | ||||
|   _sizeLandmarks=0; | ||||
|   int* blockPoseIndices = new int[_optimizer->indexMapping().size()]; | ||||
|   int* blockLandmarkIndices = new int[_optimizer->indexMapping().size()]; | ||||
| 
 | ||||
|   for (size_t i = 0; i < _optimizer->indexMapping().size(); ++i) { | ||||
|     OptimizableGraph::Vertex* v = _optimizer->indexMapping()[i]; | ||||
|     int dim = v->dimension(); | ||||
|     if (! v->marginalized()){ | ||||
|       v->setColInHessian(_sizePoses); | ||||
|       _sizePoses+=dim; | ||||
|       blockPoseIndices[_numPoses]=_sizePoses; | ||||
|       ++_numPoses; | ||||
|     } else { | ||||
|       v->setColInHessian(_sizeLandmarks); | ||||
|       _sizeLandmarks+=dim; | ||||
|       blockLandmarkIndices[_numLandmarks]=_sizeLandmarks; | ||||
|       ++_numLandmarks; | ||||
|     } | ||||
|     sparseDim += dim; | ||||
|   } | ||||
|   resize(blockPoseIndices, _numPoses, blockLandmarkIndices, _numLandmarks, sparseDim); | ||||
|   delete[] blockLandmarkIndices; | ||||
|   delete[] blockPoseIndices; | ||||
| 
 | ||||
|   // allocate the diagonal on Hpp and Hll
 | ||||
|   int poseIdx = 0; | ||||
|   int landmarkIdx = 0; | ||||
|   for (size_t i = 0; i < _optimizer->indexMapping().size(); ++i) { | ||||
|     OptimizableGraph::Vertex* v = _optimizer->indexMapping()[i]; | ||||
|     if (! v->marginalized()){ | ||||
|       //assert(poseIdx == v->hessianIndex());
 | ||||
|       PoseMatrixType* m = _Hpp->block(poseIdx, poseIdx, true); | ||||
|       if (zeroBlocks) | ||||
|         m->setZero(); | ||||
|       v->mapHessianMemory(m->data()); | ||||
|       ++poseIdx; | ||||
|     } else { | ||||
|       LandmarkMatrixType* m = _Hll->block(landmarkIdx, landmarkIdx, true); | ||||
|       if (zeroBlocks) | ||||
|         m->setZero(); | ||||
|       v->mapHessianMemory(m->data()); | ||||
|       ++landmarkIdx; | ||||
|     } | ||||
|   } | ||||
|   assert(poseIdx == _numPoses && landmarkIdx == _numLandmarks); | ||||
| 
 | ||||
|   // temporary structures for building the pattern of the Schur complement
 | ||||
|   SparseBlockMatrixHashMap<PoseMatrixType>* schurMatrixLookup = 0; | ||||
|   if (_doSchur) { | ||||
|     schurMatrixLookup = new SparseBlockMatrixHashMap<PoseMatrixType>(_Hschur->rowBlockIndices(), _Hschur->colBlockIndices()); | ||||
|     schurMatrixLookup->blockCols().resize(_Hschur->blockCols().size()); | ||||
|   } | ||||
| 
 | ||||
|   // here we assume that the landmark indices start after the pose ones
 | ||||
|   // create the structure in Hpp, Hll and in Hpl
 | ||||
|   for (SparseOptimizer::EdgeContainer::const_iterator it=_optimizer->activeEdges().begin(); it!=_optimizer->activeEdges().end(); ++it){ | ||||
|     OptimizableGraph::Edge* e = *it; | ||||
| 
 | ||||
|     for (size_t viIdx = 0; viIdx < e->vertices().size(); ++viIdx) { | ||||
|       OptimizableGraph::Vertex* v1 = (OptimizableGraph::Vertex*) e->vertex(viIdx); | ||||
|       int ind1 = v1->hessianIndex(); | ||||
|       if (ind1 == -1) | ||||
|         continue; | ||||
|       int indexV1Bak = ind1; | ||||
|       for (size_t vjIdx = viIdx + 1; vjIdx < e->vertices().size(); ++vjIdx) { | ||||
|         OptimizableGraph::Vertex* v2 = (OptimizableGraph::Vertex*) e->vertex(vjIdx); | ||||
|         int ind2 = v2->hessianIndex(); | ||||
|         if (ind2 == -1) | ||||
|           continue; | ||||
|         ind1 = indexV1Bak; | ||||
|         bool transposedBlock = ind1 > ind2; | ||||
|         if (transposedBlock){ // make sure, we allocate the upper triangle block
 | ||||
|           swap(ind1, ind2); | ||||
|         } | ||||
|         if (! v1->marginalized() && !v2->marginalized()){ | ||||
|           PoseMatrixType* m = _Hpp->block(ind1, ind2, true); | ||||
|           if (zeroBlocks) | ||||
|             m->setZero(); | ||||
|           e->mapHessianMemory(m->data(), viIdx, vjIdx, transposedBlock); | ||||
|           if (_Hschur) {// assume this is only needed in case we solve with the schur complement
 | ||||
|             schurMatrixLookup->addBlock(ind1, ind2); | ||||
|           } | ||||
|         } else if (v1->marginalized() && v2->marginalized()){ | ||||
|           // RAINER hmm.... should we ever reach this here????
 | ||||
|           LandmarkMatrixType* m = _Hll->block(ind1-_numPoses, ind2-_numPoses, true); | ||||
|           if (zeroBlocks) | ||||
|             m->setZero(); | ||||
|           e->mapHessianMemory(m->data(), viIdx, vjIdx, false); | ||||
|         } else {  | ||||
|           if (v1->marginalized()){  | ||||
|             PoseLandmarkMatrixType* m = _Hpl->block(v2->hessianIndex(),v1->hessianIndex()-_numPoses, true); | ||||
|             if (zeroBlocks) | ||||
|               m->setZero(); | ||||
|             e->mapHessianMemory(m->data(), viIdx, vjIdx, true); // transpose the block before writing to it
 | ||||
|           } else { | ||||
|             PoseLandmarkMatrixType* m = _Hpl->block(v1->hessianIndex(),v2->hessianIndex()-_numPoses, true); | ||||
|             if (zeroBlocks) | ||||
|               m->setZero(); | ||||
|             e->mapHessianMemory(m->data(), viIdx, vjIdx, false); // directly the block
 | ||||
|           } | ||||
|         } | ||||
|       } | ||||
|     } | ||||
|   } | ||||
| 
 | ||||
|   if (! _doSchur) | ||||
|     return true; | ||||
| 
 | ||||
|   _DInvSchur->diagonal().resize(landmarkIdx); | ||||
|   _Hpl->fillSparseBlockMatrixCCS(*_HplCCS); | ||||
| 
 | ||||
|   for (size_t i = 0; i < _optimizer->indexMapping().size(); ++i) { | ||||
|     OptimizableGraph::Vertex* v = _optimizer->indexMapping()[i]; | ||||
|     if (v->marginalized()){ | ||||
|       const HyperGraph::EdgeSet& vedges=v->edges(); | ||||
|       for (HyperGraph::EdgeSet::const_iterator it1=vedges.begin(); it1!=vedges.end(); ++it1){ | ||||
|         for (size_t i=0; i<(*it1)->vertices().size(); ++i) | ||||
|         { | ||||
|           OptimizableGraph::Vertex* v1= (OptimizableGraph::Vertex*) (*it1)->vertex(i); | ||||
|           if (v1->hessianIndex()==-1 || v1==v) | ||||
|             continue; | ||||
|           for  (HyperGraph::EdgeSet::const_iterator it2=vedges.begin(); it2!=vedges.end(); ++it2){ | ||||
|             for (size_t j=0; j<(*it2)->vertices().size(); ++j) | ||||
|             { | ||||
|               OptimizableGraph::Vertex* v2= (OptimizableGraph::Vertex*) (*it2)->vertex(j); | ||||
|               if (v2->hessianIndex()==-1 || v2==v) | ||||
|                 continue; | ||||
|               int i1=v1->hessianIndex(); | ||||
|               int i2=v2->hessianIndex(); | ||||
|               if (i1<=i2) { | ||||
|                 schurMatrixLookup->addBlock(i1, i2); | ||||
|               } | ||||
|             } | ||||
|           } | ||||
|         } | ||||
|       } | ||||
|     } | ||||
|   } | ||||
| 
 | ||||
|   _Hschur->takePatternFromHash(*schurMatrixLookup); | ||||
|   delete schurMatrixLookup; | ||||
|   _Hschur->fillSparseBlockMatrixCCSTransposed(*_HschurTransposedCCS); | ||||
| 
 | ||||
|   return true; | ||||
| } | ||||
| 
 | ||||
| template <typename Traits> | ||||
| bool BlockSolver<Traits>::updateStructure(const std::vector<HyperGraph::Vertex*>& vset, const HyperGraph::EdgeSet& edges) | ||||
| { | ||||
|   for (std::vector<HyperGraph::Vertex*>::const_iterator vit = vset.begin(); vit != vset.end(); ++vit) { | ||||
|     OptimizableGraph::Vertex* v = static_cast<OptimizableGraph::Vertex*>(*vit); | ||||
|     int dim = v->dimension(); | ||||
|     if (! v->marginalized()){ | ||||
|       v->setColInHessian(_sizePoses); | ||||
|       _sizePoses+=dim; | ||||
|       _Hpp->rowBlockIndices().push_back(_sizePoses); | ||||
|       _Hpp->colBlockIndices().push_back(_sizePoses); | ||||
|       _Hpp->blockCols().push_back(typename SparseBlockMatrix<PoseMatrixType>::IntBlockMap()); | ||||
|       ++_numPoses; | ||||
|       int ind = v->hessianIndex(); | ||||
|       PoseMatrixType* m = _Hpp->block(ind, ind, true); | ||||
|       v->mapHessianMemory(m->data()); | ||||
|     } else { | ||||
|       std::cerr << "updateStructure(): Schur not supported" << std::endl; | ||||
|       abort(); | ||||
|     } | ||||
|   } | ||||
|   resizeVector(_sizePoses + _sizeLandmarks); | ||||
| 
 | ||||
|   for (HyperGraph::EdgeSet::const_iterator it = edges.begin(); it != edges.end(); ++it) { | ||||
|     OptimizableGraph::Edge* e = static_cast<OptimizableGraph::Edge*>(*it); | ||||
| 
 | ||||
|     for (size_t viIdx = 0; viIdx < e->vertices().size(); ++viIdx) { | ||||
|       OptimizableGraph::Vertex* v1 = (OptimizableGraph::Vertex*) e->vertex(viIdx); | ||||
|       int ind1 = v1->hessianIndex(); | ||||
|       int indexV1Bak = ind1; | ||||
|       if (ind1 == -1) | ||||
|         continue; | ||||
|       for (size_t vjIdx = viIdx + 1; vjIdx < e->vertices().size(); ++vjIdx) { | ||||
|         OptimizableGraph::Vertex* v2 = (OptimizableGraph::Vertex*) e->vertex(vjIdx); | ||||
|         int ind2 = v2->hessianIndex(); | ||||
|         if (ind2 == -1) | ||||
|           continue; | ||||
|         ind1 = indexV1Bak; | ||||
|         bool transposedBlock = ind1 > ind2; | ||||
|         if (transposedBlock) // make sure, we allocate the upper triangular block
 | ||||
|           swap(ind1, ind2); | ||||
| 
 | ||||
|         if (! v1->marginalized() && !v2->marginalized()) { | ||||
|           PoseMatrixType* m = _Hpp->block(ind1, ind2, true); | ||||
|           e->mapHessianMemory(m->data(), viIdx, vjIdx, transposedBlock); | ||||
|         } else {  | ||||
|           std::cerr << __PRETTY_FUNCTION__ << ": not supported" << std::endl; | ||||
|         } | ||||
|       } | ||||
|     } | ||||
| 
 | ||||
|   } | ||||
| 
 | ||||
|   return true; | ||||
| } | ||||
| 
 | ||||
| template <typename Traits> | ||||
| bool BlockSolver<Traits>::solve(){ | ||||
|   //cerr << __PRETTY_FUNCTION__ << endl;
 | ||||
|   if (! _doSchur){ | ||||
|     double t=get_monotonic_time(); | ||||
|     bool ok = _linearSolver->solve(*_Hpp, _x, _b); | ||||
|     G2OBatchStatistics* globalStats = G2OBatchStatistics::globalStats(); | ||||
|     if (globalStats) { | ||||
|       globalStats->timeLinearSolver = get_monotonic_time() - t; | ||||
|       globalStats->hessianDimension = globalStats->hessianPoseDimension = _Hpp->cols(); | ||||
|     } | ||||
|     return ok; | ||||
|   } | ||||
| 
 | ||||
|   // schur thing
 | ||||
| 
 | ||||
|   // backup the coefficient matrix
 | ||||
|   double t=get_monotonic_time(); | ||||
| 
 | ||||
|   // _Hschur = _Hpp, but keeping the pattern of _Hschur
 | ||||
|   _Hschur->clear(); | ||||
|   _Hpp->add(_Hschur); | ||||
| 
 | ||||
|   //_DInvSchur->clear();
 | ||||
|   memset (_coefficients, 0, _sizePoses*sizeof(double)); | ||||
| # ifdef G2O_OPENMP | ||||
| # pragma omp parallel for default (shared) schedule(dynamic, 10) | ||||
| # endif | ||||
|   for (int landmarkIndex = 0; landmarkIndex < static_cast<int>(_Hll->blockCols().size()); ++landmarkIndex) { | ||||
|     const typename SparseBlockMatrix<LandmarkMatrixType>::IntBlockMap& marginalizeColumn = _Hll->blockCols()[landmarkIndex]; | ||||
|     assert(marginalizeColumn.size() == 1 && "more than one block in _Hll column"); | ||||
| 
 | ||||
|     // calculate inverse block for the landmark
 | ||||
|     const LandmarkMatrixType * D = marginalizeColumn.begin()->second; | ||||
|     assert (D && D->rows()==D->cols() && "Error in landmark matrix"); | ||||
|     LandmarkMatrixType& Dinv = _DInvSchur->diagonal()[landmarkIndex]; | ||||
|     Dinv = D->inverse(); | ||||
| 
 | ||||
|     LandmarkVectorType  db(D->rows()); | ||||
|     for (int j=0; j<D->rows(); ++j) { | ||||
|       db[j]=_b[_Hll->rowBaseOfBlock(landmarkIndex) + _sizePoses + j]; | ||||
|     } | ||||
|     db=Dinv*db; | ||||
| 
 | ||||
|     assert((size_t)landmarkIndex < _HplCCS->blockCols().size() && "Index out of bounds"); | ||||
|     const typename SparseBlockMatrixCCS<PoseLandmarkMatrixType>::SparseColumn& landmarkColumn = _HplCCS->blockCols()[landmarkIndex]; | ||||
| 
 | ||||
|     for (typename SparseBlockMatrixCCS<PoseLandmarkMatrixType>::SparseColumn::const_iterator it_outer = landmarkColumn.begin(); | ||||
|         it_outer != landmarkColumn.end(); ++it_outer) { | ||||
|       int i1 = it_outer->row; | ||||
| 
 | ||||
|       const PoseLandmarkMatrixType* Bi = it_outer->block; | ||||
|       assert(Bi); | ||||
| 
 | ||||
|       PoseLandmarkMatrixType BDinv = (*Bi)*(Dinv); | ||||
|       assert(_HplCCS->rowBaseOfBlock(i1) < _sizePoses && "Index out of bounds"); | ||||
|       typename PoseVectorType::MapType Bb(&_coefficients[_HplCCS->rowBaseOfBlock(i1)], Bi->rows()); | ||||
| #    ifdef G2O_OPENMP | ||||
|       ScopedOpenMPMutex mutexLock(&_coefficientsMutex[i1]); | ||||
| #    endif | ||||
|       Bb.noalias() += (*Bi)*db; | ||||
| 
 | ||||
|       assert(i1 >= 0 && i1 < static_cast<int>(_HschurTransposedCCS->blockCols().size()) && "Index out of bounds"); | ||||
|       typename SparseBlockMatrixCCS<PoseMatrixType>::SparseColumn::iterator targetColumnIt = _HschurTransposedCCS->blockCols()[i1].begin(); | ||||
| 
 | ||||
|       typename SparseBlockMatrixCCS<PoseLandmarkMatrixType>::RowBlock aux(i1, 0); | ||||
|       typename SparseBlockMatrixCCS<PoseLandmarkMatrixType>::SparseColumn::const_iterator it_inner = lower_bound(landmarkColumn.begin(), landmarkColumn.end(), aux); | ||||
|       for (; it_inner != landmarkColumn.end(); ++it_inner) { | ||||
|         int i2 = it_inner->row; | ||||
|         const PoseLandmarkMatrixType* Bj = it_inner->block; | ||||
|         assert(Bj);  | ||||
|         while (targetColumnIt->row < i2 /*&& targetColumnIt != _HschurTransposedCCS->blockCols()[i1].end()*/) | ||||
|           ++targetColumnIt; | ||||
|         assert(targetColumnIt != _HschurTransposedCCS->blockCols()[i1].end() && targetColumnIt->row == i2 && "invalid iterator, something wrong with the matrix structure"); | ||||
|         PoseMatrixType* Hi1i2 = targetColumnIt->block;//_Hschur->block(i1,i2);
 | ||||
|         assert(Hi1i2); | ||||
|         (*Hi1i2).noalias() -= BDinv*Bj->transpose(); | ||||
|       } | ||||
|     } | ||||
|   } | ||||
|   //cerr << "Solve [marginalize] = " <<  get_monotonic_time()-t << endl;
 | ||||
| 
 | ||||
|   // _bschur = _b for calling solver, and not touching _b
 | ||||
|   memcpy(_bschur, _b, _sizePoses * sizeof(double)); | ||||
|   for (int i=0; i<_sizePoses; ++i){ | ||||
|     _bschur[i]-=_coefficients[i]; | ||||
|   } | ||||
| 
 | ||||
|   G2OBatchStatistics* globalStats = G2OBatchStatistics::globalStats(); | ||||
|   if (globalStats){ | ||||
|     globalStats->timeSchurComplement = get_monotonic_time() - t; | ||||
|   } | ||||
| 
 | ||||
|   t=get_monotonic_time(); | ||||
|   bool solvedPoses = _linearSolver->solve(*_Hschur, _x, _bschur); | ||||
|   if (globalStats) { | ||||
|     globalStats->timeLinearSolver = get_monotonic_time() - t; | ||||
|     globalStats->hessianPoseDimension = _Hpp->cols(); | ||||
|     globalStats->hessianLandmarkDimension = _Hll->cols(); | ||||
|     globalStats->hessianDimension = globalStats->hessianPoseDimension + globalStats->hessianLandmarkDimension; | ||||
|   } | ||||
|   //cerr << "Solve [decompose and solve] = " <<  get_monotonic_time()-t << endl;
 | ||||
| 
 | ||||
|   if (! solvedPoses) | ||||
|     return false; | ||||
| 
 | ||||
|   // _x contains the solution for the poses, now applying it to the landmarks to get the new part of the
 | ||||
|   // solution;
 | ||||
|   double* xp = _x; | ||||
|   double* cp = _coefficients; | ||||
| 
 | ||||
|   double* xl=_x+_sizePoses; | ||||
|   double* cl=_coefficients + _sizePoses; | ||||
|   double* bl=_b+_sizePoses; | ||||
| 
 | ||||
|   // cp = -xp
 | ||||
|   for (int i=0; i<_sizePoses; ++i) | ||||
|     cp[i]=-xp[i]; | ||||
| 
 | ||||
|   // cl = bl
 | ||||
|   memcpy(cl,bl,_sizeLandmarks*sizeof(double)); | ||||
| 
 | ||||
|   // cl = bl - Bt * xp
 | ||||
|   //Bt->multiply(cl, cp);
 | ||||
|   _HplCCS->rightMultiply(cl, cp); | ||||
| 
 | ||||
|   // xl = Dinv * cl
 | ||||
|   memset(xl,0, _sizeLandmarks*sizeof(double)); | ||||
|   _DInvSchur->multiply(xl,cl); | ||||
|   //_DInvSchur->rightMultiply(xl,cl);
 | ||||
|   //cerr << "Solve [landmark delta] = " <<  get_monotonic_time()-t << endl;
 | ||||
| 
 | ||||
|   return true; | ||||
| } | ||||
| 
 | ||||
| 
 | ||||
| template <typename Traits> | ||||
| bool BlockSolver<Traits>::computeMarginals(SparseBlockMatrix<MatrixXd>& spinv, const std::vector<std::pair<int, int> >& blockIndices) | ||||
| { | ||||
|   double t = get_monotonic_time(); | ||||
|   bool ok = _linearSolver->solvePattern(spinv, blockIndices, *_Hpp); | ||||
|   G2OBatchStatistics* globalStats = G2OBatchStatistics::globalStats(); | ||||
|   if (globalStats) { | ||||
|     globalStats->timeMarginals = get_monotonic_time() - t; | ||||
|   } | ||||
|   return ok; | ||||
| } | ||||
| 
 | ||||
| template <typename Traits> | ||||
| bool BlockSolver<Traits>::buildSystem() | ||||
| { | ||||
|   // clear b vector
 | ||||
| # ifdef G2O_OPENMP | ||||
| # pragma omp parallel for default (shared) if (_optimizer->indexMapping().size() > 1000) | ||||
| # endif | ||||
|   for (int i = 0; i < static_cast<int>(_optimizer->indexMapping().size()); ++i) { | ||||
|     OptimizableGraph::Vertex* v=_optimizer->indexMapping()[i]; | ||||
|     assert(v); | ||||
|     v->clearQuadraticForm(); | ||||
|   } | ||||
|   _Hpp->clear(); | ||||
|   if (_doSchur) { | ||||
|     _Hll->clear(); | ||||
|     _Hpl->clear(); | ||||
|   } | ||||
| 
 | ||||
|   // resetting the terms for the pairwise constraints
 | ||||
|   // built up the current system by storing the Hessian blocks in the edges and vertices
 | ||||
| # ifndef G2O_OPENMP | ||||
|   // no threading, we do not need to copy the workspace
 | ||||
|   JacobianWorkspace& jacobianWorkspace = _optimizer->jacobianWorkspace(); | ||||
| # else | ||||
|   // if running with threads need to produce copies of the workspace for each thread
 | ||||
|   JacobianWorkspace jacobianWorkspace = _optimizer->jacobianWorkspace(); | ||||
| # pragma omp parallel for default (shared) firstprivate(jacobianWorkspace) if (_optimizer->activeEdges().size() > 100) | ||||
| # endif | ||||
|   for (int k = 0; k < static_cast<int>(_optimizer->activeEdges().size()); ++k) { | ||||
|     OptimizableGraph::Edge* e = _optimizer->activeEdges()[k]; | ||||
|     e->linearizeOplus(jacobianWorkspace); // jacobian of the nodes' oplus (manifold)
 | ||||
|     e->constructQuadraticForm(); | ||||
| #  ifndef NDEBUG | ||||
|     for (size_t i = 0; i < e->vertices().size(); ++i) { | ||||
|       const OptimizableGraph::Vertex* v = static_cast<const OptimizableGraph::Vertex*>(e->vertex(i)); | ||||
|       if (! v->fixed()) { | ||||
|         bool hasANan = arrayHasNaN(jacobianWorkspace.workspaceForVertex(i), e->dimension() * v->dimension()); | ||||
|         if (hasANan) { | ||||
|           cerr << "buildSystem(): NaN within Jacobian for edge " << e << " for vertex " << i << endl; | ||||
|           break; | ||||
|         } | ||||
|       } | ||||
|     } | ||||
| #  endif | ||||
|   } | ||||
| 
 | ||||
|   // flush the current system in a sparse block matrix
 | ||||
| # ifdef G2O_OPENMP | ||||
| # pragma omp parallel for default (shared) if (_optimizer->indexMapping().size() > 1000) | ||||
| # endif | ||||
|   for (int i = 0; i < static_cast<int>(_optimizer->indexMapping().size()); ++i) { | ||||
|     OptimizableGraph::Vertex* v=_optimizer->indexMapping()[i]; | ||||
|     int iBase = v->colInHessian(); | ||||
|     if (v->marginalized()) | ||||
|       iBase+=_sizePoses; | ||||
|     v->copyB(_b+iBase); | ||||
|   } | ||||
| 
 | ||||
|   return 0; | ||||
| } | ||||
| 
 | ||||
| 
 | ||||
| template <typename Traits> | ||||
| bool BlockSolver<Traits>::setLambda(double lambda, bool backup) | ||||
| { | ||||
|   if (backup) { | ||||
|     _diagonalBackupPose.resize(_numPoses); | ||||
|     _diagonalBackupLandmark.resize(_numLandmarks); | ||||
|   } | ||||
| # ifdef G2O_OPENMP | ||||
| # pragma omp parallel for default (shared) if (_numPoses > 100) | ||||
| # endif | ||||
|   for (int i = 0; i < _numPoses; ++i) { | ||||
|     PoseMatrixType *b=_Hpp->block(i,i); | ||||
|     if (backup) | ||||
|       _diagonalBackupPose[i] = b->diagonal(); | ||||
|     b->diagonal().array() += lambda; | ||||
|   } | ||||
| # ifdef G2O_OPENMP | ||||
| # pragma omp parallel for default (shared) if (_numLandmarks > 100) | ||||
| # endif | ||||
|   for (int i = 0; i < _numLandmarks; ++i) { | ||||
|     LandmarkMatrixType *b=_Hll->block(i,i); | ||||
|     if (backup) | ||||
|       _diagonalBackupLandmark[i] = b->diagonal(); | ||||
|     b->diagonal().array() += lambda; | ||||
|   } | ||||
|   return true; | ||||
| } | ||||
| 
 | ||||
| template <typename Traits> | ||||
| void BlockSolver<Traits>::restoreDiagonal() | ||||
| { | ||||
|   assert((int) _diagonalBackupPose.size() == _numPoses && "Mismatch in dimensions"); | ||||
|   assert((int) _diagonalBackupLandmark.size() == _numLandmarks && "Mismatch in dimensions"); | ||||
|   for (int i = 0; i < _numPoses; ++i) { | ||||
|     PoseMatrixType *b=_Hpp->block(i,i); | ||||
|     b->diagonal() = _diagonalBackupPose[i]; | ||||
|   } | ||||
|   for (int i = 0; i < _numLandmarks; ++i) { | ||||
|     LandmarkMatrixType *b=_Hll->block(i,i); | ||||
|     b->diagonal() = _diagonalBackupLandmark[i]; | ||||
|   } | ||||
| } | ||||
| 
 | ||||
| template <typename Traits> | ||||
| bool BlockSolver<Traits>::init(SparseOptimizer* optimizer, bool online) | ||||
| { | ||||
|   _optimizer = optimizer; | ||||
|   if (! online) { | ||||
|     if (_Hpp) | ||||
|       _Hpp->clear(); | ||||
|     if (_Hpl) | ||||
|       _Hpl->clear(); | ||||
|     if (_Hll) | ||||
|       _Hll->clear(); | ||||
|   } | ||||
|   _linearSolver->init(); | ||||
|   return true; | ||||
| } | ||||
| 
 | ||||
| template <typename Traits> | ||||
| void BlockSolver<Traits>::setWriteDebug(bool writeDebug) | ||||
| { | ||||
|   _linearSolver->setWriteDebug(writeDebug); | ||||
| } | ||||
| 
 | ||||
| template <typename Traits> | ||||
| bool BlockSolver<Traits>::saveHessian(const std::string& fileName) const | ||||
| { | ||||
|   return _Hpp->writeOctave(fileName.c_str(), true); | ||||
| } | ||||
| 
 | ||||
| } // end namespace
 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
							
								
								
									
										183
									
								
								SLAM/Thirdparty/g2o/g2o/core/cache.cpp
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										183
									
								
								SLAM/Thirdparty/g2o/g2o/core/cache.cpp
									
									
									
									
										vendored
									
									
								
							| @ -1,183 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 G. Grisetti, R. Kuemmerle, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| #include "cache.h" | ||||
| #include "optimizable_graph.h" | ||||
| #include "factory.h" | ||||
| 
 | ||||
| #include <iostream> | ||||
| 
 | ||||
| namespace g2o { | ||||
|   using namespace std; | ||||
| 
 | ||||
|   Cache::CacheKey::CacheKey() : | ||||
|     _type(), _parameters() | ||||
|   { | ||||
|   } | ||||
| 
 | ||||
|   Cache::CacheKey::CacheKey(const std::string& type_, const ParameterVector& parameters_) : | ||||
|     _type(type_), _parameters(parameters_) | ||||
|   { | ||||
|   } | ||||
| 
 | ||||
|   Cache::Cache(CacheContainer* container_, const ParameterVector& parameters_) : | ||||
|     _updateNeeded(true), _parameters(parameters_), _container(container_) | ||||
|   { | ||||
|   } | ||||
| 
 | ||||
|   bool Cache::CacheKey::operator<(const Cache::CacheKey& c) const{ | ||||
|     if (_type < c._type) | ||||
|       return true; | ||||
|     return std::lexicographical_compare (_parameters.begin( ), _parameters.end( ), | ||||
|            c._parameters.begin( ), c._parameters.end( ) ); | ||||
|   } | ||||
| 
 | ||||
| 
 | ||||
|   OptimizableGraph::Vertex* Cache::vertex() {  | ||||
|     if (container() )  | ||||
|       return container()->vertex();  | ||||
|     return 0;  | ||||
|   } | ||||
| 
 | ||||
|   OptimizableGraph* Cache::graph() { | ||||
|     if (container()) | ||||
|       return container()->graph(); | ||||
|     return 0; | ||||
|   } | ||||
| 
 | ||||
|   CacheContainer* Cache::container() { | ||||
|     return _container; | ||||
|   } | ||||
| 
 | ||||
|   ParameterVector& Cache::parameters() { | ||||
|     return _parameters; | ||||
|   } | ||||
|    | ||||
|   Cache::CacheKey Cache::key() const { | ||||
|     Factory* factory=Factory::instance(); | ||||
|     return CacheKey(factory->tag(this), _parameters); | ||||
|   }; | ||||
| 
 | ||||
|    | ||||
|   void Cache::update(){ | ||||
|     if (! _updateNeeded) | ||||
|       return; | ||||
|     for(std::vector<Cache*>::iterator it=_parentCaches.begin(); it!=_parentCaches.end(); it++){ | ||||
|       (*it)->update(); | ||||
|     } | ||||
|     updateImpl(); | ||||
|     _updateNeeded=false; | ||||
|   } | ||||
| 
 | ||||
|   Cache* Cache::installDependency(const std::string& type_, const std::vector<int>& parameterIndices){ | ||||
|     ParameterVector pv(parameterIndices.size()); | ||||
|     for (size_t i=0; i<parameterIndices.size(); i++){ | ||||
|       if (parameterIndices[i]<0 || parameterIndices[i] >=(int)_parameters.size()) | ||||
|   return 0; | ||||
|       pv[i]=_parameters[ parameterIndices[i] ]; | ||||
|     } | ||||
|     CacheKey k(type_, pv); | ||||
|     if (!container()) | ||||
|       return 0; | ||||
|     Cache* c=container()->findCache(k); | ||||
|     if (!c) { | ||||
|       c = container()->createCache(k); | ||||
|     } | ||||
|     if (c) | ||||
|       _parentCaches.push_back(c); | ||||
|     return c; | ||||
|   } | ||||
|    | ||||
|   bool Cache::resolveDependancies(){ | ||||
|     return true; | ||||
|   } | ||||
| 
 | ||||
|   CacheContainer::CacheContainer(OptimizableGraph::Vertex* vertex_) { | ||||
|     _vertex = vertex_; | ||||
|   } | ||||
| 
 | ||||
|   Cache* CacheContainer::findCache(const Cache::CacheKey& key) { | ||||
|     iterator it=find(key); | ||||
|     if (it==end()) | ||||
|       return 0; | ||||
|     return it->second; | ||||
|   } | ||||
|    | ||||
|   Cache* CacheContainer::createCache(const Cache::CacheKey& key){ | ||||
|     Factory* f = Factory::instance(); | ||||
|     HyperGraph::HyperGraphElement* e = f->construct(key.type()); | ||||
|     if (!e) { | ||||
|       cerr << __PRETTY_FUNCTION__ << endl; | ||||
|       cerr << "fatal error in creating cache of type " << key.type() << endl; | ||||
|       return 0; | ||||
|     } | ||||
|     Cache* c = dynamic_cast<Cache*>(e); | ||||
|     if (! c){ | ||||
|       cerr << __PRETTY_FUNCTION__ << endl; | ||||
|       cerr << "fatal error in creating cache of type " << key.type() << endl; | ||||
|       return 0; | ||||
|     } | ||||
|     c->_container = this; | ||||
|     c->_parameters = key._parameters; | ||||
|     if (c->resolveDependancies()){ | ||||
|       insert(make_pair(key,c)); | ||||
|       c->update(); | ||||
|       return c; | ||||
|     }  | ||||
|     return 0; | ||||
|   } | ||||
|    | ||||
|   OptimizableGraph::Vertex* CacheContainer::vertex() { | ||||
|     return _vertex; | ||||
|   } | ||||
| 
 | ||||
|   OptimizableGraph* CacheContainer::graph(){ | ||||
|     if (_vertex) | ||||
|       return _vertex->graph(); | ||||
|     return 0; | ||||
|   } | ||||
| 
 | ||||
|   void CacheContainer::update() { | ||||
|     for (iterator it=begin(); it!=end(); it++){ | ||||
|       (it->second)->update(); | ||||
|     } | ||||
|     _updateNeeded=false; | ||||
|   } | ||||
| 
 | ||||
|   void CacheContainer::setUpdateNeeded(bool needUpdate) { | ||||
|     _updateNeeded=needUpdate; | ||||
|     for (iterator it=begin(); it!=end(); ++it){ | ||||
|       (it->second)->_updateNeeded = needUpdate; | ||||
|     } | ||||
|   } | ||||
| 
 | ||||
|   CacheContainer::~CacheContainer(){ | ||||
|     for (iterator it=begin(); it!=end(); ++it){ | ||||
|       delete (it->second); | ||||
|     } | ||||
|   } | ||||
| 
 | ||||
| } // end namespace
 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
							
								
								
									
										140
									
								
								SLAM/Thirdparty/g2o/g2o/core/cache.h
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										140
									
								
								SLAM/Thirdparty/g2o/g2o/core/cache.h
									
									
									
									
										vendored
									
									
								
							| @ -1,140 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 R. Kuemmerle, G. Grisetti, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| #ifndef G2O_CACHE_HH_ | ||||
| #define G2O_CACHE_HH_ | ||||
| 
 | ||||
| #include <map> | ||||
| 
 | ||||
| #include "optimizable_graph.h" | ||||
| 
 | ||||
| namespace g2o { | ||||
| 
 | ||||
|   class CacheContainer; | ||||
|    | ||||
|   class  Cache: public HyperGraph::HyperGraphElement | ||||
|   { | ||||
|     public: | ||||
|       friend class CacheContainer; | ||||
|       class  CacheKey | ||||
|       { | ||||
|         public: | ||||
|           friend class CacheContainer; | ||||
|           CacheKey(); | ||||
|           CacheKey(const std::string& type_, const ParameterVector& parameters_); | ||||
| 
 | ||||
|           bool operator<(const CacheKey& c) const; | ||||
| 
 | ||||
|           const std::string& type() const { return _type;} | ||||
|           const ParameterVector& parameters() const { return _parameters;} | ||||
| 
 | ||||
|         protected: | ||||
|           std::string _type; | ||||
|           ParameterVector _parameters; | ||||
|       }; | ||||
| 
 | ||||
|       Cache(CacheContainer* container_ = 0, const ParameterVector& parameters_ = ParameterVector()); | ||||
| 
 | ||||
|       CacheKey key() const; | ||||
| 
 | ||||
|       OptimizableGraph::Vertex* vertex(); | ||||
|       OptimizableGraph* graph(); | ||||
|       CacheContainer* container(); | ||||
|       ParameterVector& parameters(); | ||||
| 
 | ||||
|       void update(); | ||||
| 
 | ||||
|       virtual HyperGraph::HyperGraphElementType elementType() const { return HyperGraph::HGET_CACHE;} | ||||
| 
 | ||||
|     protected: | ||||
|       //! redefine this to do the update
 | ||||
|       virtual void updateImpl() = 0; | ||||
| 
 | ||||
|       /**
 | ||||
|        * this function installs and satisfies a cache | ||||
|        * @param type_: the typename of the dependency | ||||
|        * @param parameterIndices: a vector containing the indices if the parameters | ||||
|        * in _parameters that will be used to assemble the Key of the cache being created | ||||
|        * For example if I have a cache of type C2, having parameters "A, B, and C", | ||||
|        * and it depends on a cache of type C1 that depends on the parameters A and C,  | ||||
|        * the parameterIndices should contain "0, 2", since they are the positions in the | ||||
|        * parameter vector of C2 of the parameters needed to construct C1. | ||||
|        * @returns the newly created cache | ||||
|        */ | ||||
|       Cache* installDependency(const std::string& type_, const std::vector<int>& parameterIndices); | ||||
| 
 | ||||
|       /**
 | ||||
|        * Function to be called from a cache that has dependencies. It just invokes a | ||||
|        * sequence of installDependency(). | ||||
|        * Although the caches returned are stored in the _parentCache vector, | ||||
|        * it is better that you redefine your own cache member variables, for better readability | ||||
|        */ | ||||
|       virtual bool resolveDependancies(); | ||||
| 
 | ||||
|       bool _updateNeeded; | ||||
|       ParameterVector _parameters; | ||||
|       std::vector<Cache*> _parentCaches; | ||||
|       CacheContainer* _container; | ||||
|   }; | ||||
| 
 | ||||
|   class  CacheContainer: public std::map<Cache::CacheKey, Cache*> | ||||
|   { | ||||
|     public: | ||||
|       CacheContainer(OptimizableGraph::Vertex* vertex_); | ||||
|       virtual ~CacheContainer(); | ||||
|       OptimizableGraph::Vertex* vertex(); | ||||
|       OptimizableGraph* graph(); | ||||
|       Cache* findCache(const Cache::CacheKey& key); | ||||
|       Cache* createCache(const Cache::CacheKey& key); | ||||
|       void setUpdateNeeded(bool needUpdate=true); | ||||
|       void update(); | ||||
|     protected: | ||||
|       OptimizableGraph::Vertex* _vertex; | ||||
|       bool _updateNeeded; | ||||
|   }; | ||||
| 
 | ||||
| 
 | ||||
|   template <typename CacheType> | ||||
|   void OptimizableGraph::Edge::resolveCache(CacheType*& cache,  | ||||
|       OptimizableGraph::Vertex* v,  | ||||
|       const std::string& type_,  | ||||
|       const ParameterVector& parameters_) | ||||
|   { | ||||
|     cache = 0; | ||||
|     CacheContainer* container= v->cacheContainer(); | ||||
|     Cache::CacheKey key(type_, parameters_); | ||||
|     Cache* c = container->findCache(key); | ||||
|     if (!c) { | ||||
|       c = container->createCache(key); | ||||
|     } | ||||
|     if (c) { | ||||
|       cache = dynamic_cast<CacheType*>(c);  | ||||
|     } | ||||
|   } | ||||
| 
 | ||||
| } // end namespace
 | ||||
| 
 | ||||
| #endif | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
							
								
								
									
										75
									
								
								SLAM/Thirdparty/g2o/g2o/core/creators.h
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										75
									
								
								SLAM/Thirdparty/g2o/g2o/core/creators.h
									
									
									
									
										vendored
									
									
								
							| @ -1,75 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 R. Kuemmerle, G. Grisetti, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| #ifndef G2O_CREATORS_H | ||||
| #define G2O_CREATORS_H | ||||
| 
 | ||||
| #include "hyper_graph.h" | ||||
| 
 | ||||
| #include <string> | ||||
| #include <typeinfo> | ||||
| 
 | ||||
| namespace g2o | ||||
| { | ||||
| 
 | ||||
|   /**
 | ||||
|    * \brief Abstract interface for allocating HyperGraphElement | ||||
|    */ | ||||
|   class  AbstractHyperGraphElementCreator | ||||
|   { | ||||
|     public: | ||||
|       /**
 | ||||
|        * create a hyper graph element. Has to implemented in derived class. | ||||
|        */ | ||||
|       virtual HyperGraph::HyperGraphElement* construct() = 0; | ||||
|       /**
 | ||||
|        * name of the class to be created. Has to implemented in derived class. | ||||
|        */ | ||||
|       virtual const std::string& name() const = 0; | ||||
| 
 | ||||
|       virtual ~AbstractHyperGraphElementCreator() { } | ||||
|   }; | ||||
| 
 | ||||
|   /**
 | ||||
|    * \brief templatized creator class which creates graph elements | ||||
|    */ | ||||
|   template <typename T> | ||||
|   class HyperGraphElementCreator : public AbstractHyperGraphElementCreator | ||||
|   { | ||||
|     public: | ||||
|       HyperGraphElementCreator() : _name(typeid(T).name()) {} | ||||
| #if defined (WINDOWS) && defined(__GNUC__) // force stack alignment on Windows with GCC
 | ||||
|       __attribute__((force_align_arg_pointer)) | ||||
| #endif | ||||
|       HyperGraph::HyperGraphElement* construct() { return new T;} | ||||
|       virtual const std::string& name() const { return _name;} | ||||
|     protected: | ||||
|       std::string _name; | ||||
|   }; | ||||
| 
 | ||||
| } // end namespace
 | ||||
| 
 | ||||
| #endif | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
							
								
								
									
										73
									
								
								SLAM/Thirdparty/g2o/g2o/core/eigen_types.h
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										73
									
								
								SLAM/Thirdparty/g2o/g2o/core/eigen_types.h
									
									
									
									
										vendored
									
									
								
							| @ -1,73 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 R. Kuemmerle, G. Grisetti, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| #ifndef G2O_EIGEN_TYPES_H | ||||
| #define G2O_EIGEN_TYPES_H | ||||
| 
 | ||||
| #include <Eigen/Core> | ||||
| #include <Eigen/Geometry> | ||||
| 
 | ||||
| namespace g2o { | ||||
| 
 | ||||
|   typedef Eigen::Matrix<int,2,1,Eigen::ColMajor>                                  Vector2I; | ||||
|   typedef Eigen::Matrix<int,3,1,Eigen::ColMajor>                                  Vector3I; | ||||
|   typedef Eigen::Matrix<int,4,1,Eigen::ColMajor>                                  Vector4I; | ||||
|   typedef Eigen::Matrix<int,Eigen::Dynamic,1,Eigen::ColMajor>                     VectorXI;  | ||||
| 
 | ||||
|   typedef Eigen::Matrix<float,2,1,Eigen::ColMajor>                                Vector2F;  | ||||
|   typedef Eigen::Matrix<float,3,1,Eigen::ColMajor>                                Vector3F;  | ||||
|   typedef Eigen::Matrix<float,4,1,Eigen::ColMajor>                                Vector4F;  | ||||
|   typedef Eigen::Matrix<float,Eigen::Dynamic,1,Eigen::ColMajor>                   VectorXF;  | ||||
| 
 | ||||
|   typedef Eigen::Matrix<double,2,1,Eigen::ColMajor>                               Vector2D; | ||||
|   typedef Eigen::Matrix<double,3,1,Eigen::ColMajor>                               Vector3D; | ||||
|   typedef Eigen::Matrix<double,4,1,Eigen::ColMajor>                               Vector4D; | ||||
|   typedef Eigen::Matrix<double,Eigen::Dynamic,1,Eigen::ColMajor>                  VectorXD; | ||||
| 
 | ||||
|   typedef Eigen::Matrix<int,2,2,Eigen::ColMajor>                                  Matrix2I; | ||||
|   typedef Eigen::Matrix<int,3,3,Eigen::ColMajor>                                  Matrix3I; | ||||
|   typedef Eigen::Matrix<int,4,4,Eigen::ColMajor>                                  Matrix4I; | ||||
|   typedef Eigen::Matrix<int,Eigen::Dynamic,Eigen::Dynamic,Eigen::ColMajor>        MatrixXI; | ||||
| 
 | ||||
|   typedef Eigen::Matrix<float,2,2,Eigen::ColMajor>                                Matrix2F; | ||||
|   typedef Eigen::Matrix<float,3,3,Eigen::ColMajor>                                Matrix3F; | ||||
|   typedef Eigen::Matrix<float,4,4,Eigen::ColMajor>                                Matrix4F; | ||||
|   typedef Eigen::Matrix<float,Eigen::Dynamic,Eigen::Dynamic,Eigen::ColMajor>      MatrixXF; | ||||
| 
 | ||||
|   typedef Eigen::Matrix<double,2,2,Eigen::ColMajor>                               Matrix2D; | ||||
|   typedef Eigen::Matrix<double,3,3,Eigen::ColMajor>                               Matrix3D; | ||||
|   typedef Eigen::Matrix<double,4,4,Eigen::ColMajor>                               Matrix4D; | ||||
|   typedef Eigen::Matrix<double,Eigen::Dynamic,Eigen::Dynamic,Eigen::ColMajor>     MatrixXD; | ||||
| 
 | ||||
|   typedef Eigen::Transform<double,2,Eigen::Isometry,Eigen::ColMajor>              Isometry2D; | ||||
|   typedef Eigen::Transform<double,3,Eigen::Isometry,Eigen::ColMajor>              Isometry3D; | ||||
| 
 | ||||
|   typedef Eigen::Transform<double,2,Eigen::Affine,Eigen::ColMajor>                Affine2D; | ||||
|   typedef Eigen::Transform<double,3,Eigen::Affine,Eigen::ColMajor>                Affine3D; | ||||
| 
 | ||||
| } // end namespace g2o
 | ||||
| 
 | ||||
| #endif | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
							
								
								
									
										267
									
								
								SLAM/Thirdparty/g2o/g2o/core/estimate_propagator.cpp
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										267
									
								
								SLAM/Thirdparty/g2o/g2o/core/estimate_propagator.cpp
									
									
									
									
										vendored
									
									
								
							| @ -1,267 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 R. Kuemmerle, G. Grisetti, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| #include "estimate_propagator.h" | ||||
| 
 | ||||
| #include <queue> | ||||
| #include <vector> | ||||
| #include <cassert> | ||||
| #include <iostream> | ||||
| #include <algorithm> | ||||
| #include <fstream> | ||||
| 
 | ||||
| //#define DEBUG_ESTIMATE_PROPAGATOR
 | ||||
| 
 | ||||
| using namespace std; | ||||
| 
 | ||||
| namespace g2o { | ||||
| 
 | ||||
| # ifdef DEBUG_ESTIMATE_PROPAGATOR | ||||
|   struct FrontierLevelCmp { | ||||
|     bool operator()(EstimatePropagator::AdjacencyMapEntry* e1, EstimatePropagator::AdjacencyMapEntry* e2) const | ||||
|     { | ||||
|       return e1->frontierLevel() < e2->frontierLevel(); | ||||
|     } | ||||
|   }; | ||||
| # endif | ||||
| 
 | ||||
|   EstimatePropagator::AdjacencyMapEntry::AdjacencyMapEntry() | ||||
|   { | ||||
|     reset(); | ||||
|   } | ||||
| 
 | ||||
|   void EstimatePropagator::AdjacencyMapEntry::reset() | ||||
|   { | ||||
|     _child = 0; | ||||
|     _parent.clear(); | ||||
|     _edge = 0; | ||||
|     _distance = numeric_limits<double>::max(); | ||||
|     _frontierLevel = -1; | ||||
|     inQueue = false; | ||||
|   } | ||||
| 
 | ||||
|   EstimatePropagator::EstimatePropagator(OptimizableGraph* g): _graph(g) | ||||
|   { | ||||
|     for (OptimizableGraph::VertexIDMap::const_iterator it=_graph->vertices().begin(); it!=_graph->vertices().end(); ++it){ | ||||
|       AdjacencyMapEntry entry; | ||||
|       entry._child = static_cast<OptimizableGraph::Vertex*>(it->second); | ||||
|       _adjacencyMap.insert(make_pair(entry.child(), entry)); | ||||
|     } | ||||
|   } | ||||
| 
 | ||||
|   void EstimatePropagator::reset() | ||||
|   { | ||||
|     for (OptimizableGraph::VertexSet::iterator it=_visited.begin(); it!=_visited.end(); ++it){ | ||||
|       OptimizableGraph::Vertex* v = static_cast<OptimizableGraph::Vertex*>(*it); | ||||
|       AdjacencyMap::iterator at = _adjacencyMap.find(v); | ||||
|       assert(at != _adjacencyMap.end()); | ||||
|       at->second.reset(); | ||||
|     } | ||||
|     _visited.clear(); | ||||
|   } | ||||
| 
 | ||||
|   void EstimatePropagator::propagate(OptimizableGraph::Vertex* v,  | ||||
|       const EstimatePropagator::PropagateCost& cost,  | ||||
|        const EstimatePropagator::PropagateAction& action, | ||||
|        double maxDistance,  | ||||
|        double maxEdgeCost) | ||||
|   { | ||||
|     OptimizableGraph::VertexSet vset; | ||||
|     vset.insert(v); | ||||
|     propagate(vset, cost, action, maxDistance, maxEdgeCost); | ||||
|   } | ||||
| 
 | ||||
|   void EstimatePropagator::propagate(OptimizableGraph::VertexSet& vset,  | ||||
|       const EstimatePropagator::PropagateCost& cost,  | ||||
|        const EstimatePropagator::PropagateAction& action, | ||||
|        double maxDistance,  | ||||
|        double maxEdgeCost) | ||||
|   { | ||||
|     reset(); | ||||
| 
 | ||||
|     PriorityQueue frontier; | ||||
|     for (OptimizableGraph::VertexSet::iterator vit=vset.begin(); vit!=vset.end(); ++vit){ | ||||
|       OptimizableGraph::Vertex* v = static_cast<OptimizableGraph::Vertex*>(*vit); | ||||
|       AdjacencyMap::iterator it = _adjacencyMap.find(v); | ||||
|       assert(it != _adjacencyMap.end()); | ||||
|       it->second._distance = 0.; | ||||
|       it->second._parent.clear(); | ||||
|       it->second._frontierLevel = 0; | ||||
|       frontier.push(&it->second); | ||||
|     } | ||||
| 
 | ||||
|     while(! frontier.empty()){ | ||||
|       AdjacencyMapEntry* entry = frontier.pop(); | ||||
|       OptimizableGraph::Vertex* u = entry->child(); | ||||
|       double uDistance = entry->distance(); | ||||
|       //cerr << "uDistance " << uDistance << endl;
 | ||||
| 
 | ||||
|       // initialize the vertex
 | ||||
|       if (entry->_frontierLevel > 0) { | ||||
|         action(entry->edge(), entry->parent(), u); | ||||
|       } | ||||
| 
 | ||||
|       /* std::pair< OptimizableGraph::VertexSet::iterator, bool> insertResult = */ _visited.insert(u); | ||||
|       OptimizableGraph::EdgeSet::iterator et = u->edges().begin(); | ||||
|       while (et != u->edges().end()){ | ||||
|         OptimizableGraph::Edge* edge = static_cast<OptimizableGraph::Edge*>(*et); | ||||
|         ++et; | ||||
| 
 | ||||
|         int maxFrontier = -1; | ||||
|         OptimizableGraph::VertexSet initializedVertices; | ||||
|         for (size_t i = 0; i < edge->vertices().size(); ++i) { | ||||
|           OptimizableGraph::Vertex* z = static_cast<OptimizableGraph::Vertex*>(edge->vertex(i)); | ||||
|           AdjacencyMap::iterator ot = _adjacencyMap.find(z); | ||||
|           if (ot->second._distance != numeric_limits<double>::max()) { | ||||
|             initializedVertices.insert(z); | ||||
|             maxFrontier = (max)(maxFrontier, ot->second._frontierLevel); | ||||
|           } | ||||
|         } | ||||
|         assert(maxFrontier >= 0); | ||||
| 
 | ||||
|         for (size_t i = 0; i < edge->vertices().size(); ++i) { | ||||
|           OptimizableGraph::Vertex* z = static_cast<OptimizableGraph::Vertex*>(edge->vertex(i)); | ||||
|           if (z == u) | ||||
|             continue; | ||||
| 
 | ||||
|           size_t wasInitialized = initializedVertices.erase(z); | ||||
| 
 | ||||
|           double edgeDistance = cost(edge, initializedVertices, z); | ||||
|           if (edgeDistance > 0. && edgeDistance != std::numeric_limits<double>::max() && edgeDistance < maxEdgeCost) { | ||||
|             double zDistance = uDistance + edgeDistance; | ||||
|             //cerr << z->id() << " " << zDistance << endl;
 | ||||
| 
 | ||||
|             AdjacencyMap::iterator ot = _adjacencyMap.find(z); | ||||
|             assert(ot!=_adjacencyMap.end()); | ||||
| 
 | ||||
|             if (zDistance < ot->second.distance() && zDistance < maxDistance){ | ||||
|               //if (ot->second.inQueue)
 | ||||
|                 //cerr << "Updating" << endl;
 | ||||
|               ot->second._distance = zDistance; | ||||
|               ot->second._parent = initializedVertices; | ||||
|               ot->second._edge = edge; | ||||
|               ot->second._frontierLevel = maxFrontier + 1; | ||||
|               frontier.push(&ot->second); | ||||
|             } | ||||
|           } | ||||
| 
 | ||||
|           if (wasInitialized > 0) | ||||
|             initializedVertices.insert(z); | ||||
| 
 | ||||
|         } | ||||
|       } | ||||
|     } | ||||
| 
 | ||||
|     // writing debug information like cost for reaching each vertex and the parent used to initialize
 | ||||
| #ifdef DEBUG_ESTIMATE_PROPAGATOR | ||||
|     cerr << "Writing cost.dat" << endl; | ||||
|     ofstream costStream("cost.dat"); | ||||
|     for (AdjacencyMap::const_iterator it = _adjacencyMap.begin(); it != _adjacencyMap.end(); ++it) { | ||||
|       HyperGraph::Vertex* u = it->second.child(); | ||||
|       costStream << "vertex " << u->id() << "  cost " << it->second._distance << endl; | ||||
|     } | ||||
|     cerr << "Writing init.dat" << endl; | ||||
|     ofstream initStream("init.dat"); | ||||
|     vector<AdjacencyMapEntry*> frontierLevels; | ||||
|     for (AdjacencyMap::iterator it = _adjacencyMap.begin(); it != _adjacencyMap.end(); ++it) { | ||||
|       if (it->second._frontierLevel > 0) | ||||
|         frontierLevels.push_back(&it->second); | ||||
|     } | ||||
|     sort(frontierLevels.begin(), frontierLevels.end(), FrontierLevelCmp()); | ||||
|     for (vector<AdjacencyMapEntry*>::const_iterator it = frontierLevels.begin(); it != frontierLevels.end(); ++it) { | ||||
|       AdjacencyMapEntry* entry       = *it; | ||||
|       OptimizableGraph::Vertex* to   = entry->child(); | ||||
| 
 | ||||
|       initStream << "calling init level = " << entry->_frontierLevel << "\t ("; | ||||
|       for (OptimizableGraph::VertexSet::iterator pit = entry->parent().begin(); pit != entry->parent().end(); ++pit) { | ||||
|         initStream << " " << (*pit)->id(); | ||||
|       } | ||||
|       initStream << " ) -> " << to->id() << endl; | ||||
|     } | ||||
| #endif | ||||
| 
 | ||||
|   } | ||||
| 
 | ||||
|   void EstimatePropagator::PriorityQueue::push(AdjacencyMapEntry* entry) | ||||
|   { | ||||
|     assert(entry != NULL); | ||||
|     if (entry->inQueue) { | ||||
|       assert(entry->queueIt->second == entry); | ||||
|       erase(entry->queueIt); | ||||
|     } | ||||
| 
 | ||||
|     entry->queueIt = insert(std::make_pair(entry->distance(), entry)); | ||||
|     assert(entry->queueIt != end()); | ||||
|     entry->inQueue = true; | ||||
|   } | ||||
| 
 | ||||
|   EstimatePropagator::AdjacencyMapEntry* EstimatePropagator::PriorityQueue::pop() | ||||
|   { | ||||
|     assert(!empty()); | ||||
|     iterator it = begin(); | ||||
|     AdjacencyMapEntry* entry = it->second; | ||||
|     erase(it); | ||||
| 
 | ||||
|     assert(entry != NULL); | ||||
|     entry->queueIt = end(); | ||||
|     entry->inQueue = false; | ||||
|     return entry; | ||||
|   } | ||||
| 
 | ||||
|   EstimatePropagatorCost::EstimatePropagatorCost (SparseOptimizer* graph) : | ||||
|     _graph(graph) | ||||
|   { | ||||
|   } | ||||
| 
 | ||||
|   double EstimatePropagatorCost::operator()(OptimizableGraph::Edge* edge, const OptimizableGraph::VertexSet& from, OptimizableGraph::Vertex* to_) const | ||||
|   { | ||||
|     OptimizableGraph::Edge* e = dynamic_cast<OptimizableGraph::Edge*>(edge); | ||||
|     OptimizableGraph::Vertex* to = dynamic_cast<OptimizableGraph::Vertex*>(to_); | ||||
|     SparseOptimizer::EdgeContainer::const_iterator it = _graph->findActiveEdge(e); | ||||
|     if (it == _graph->activeEdges().end()) // it has to be an active edge
 | ||||
|       return std::numeric_limits<double>::max(); | ||||
|     return e->initialEstimatePossible(from, to); | ||||
|   } | ||||
| 
 | ||||
|   EstimatePropagatorCostOdometry::EstimatePropagatorCostOdometry(SparseOptimizer* graph) : | ||||
|     EstimatePropagatorCost(graph) | ||||
|   { | ||||
|   } | ||||
| 
 | ||||
|   double EstimatePropagatorCostOdometry::operator()(OptimizableGraph::Edge* edge, const OptimizableGraph::VertexSet& from_, OptimizableGraph::Vertex* to_) const | ||||
|   { | ||||
|     OptimizableGraph::Edge* e = dynamic_cast<OptimizableGraph::Edge*>(edge); | ||||
|     OptimizableGraph::Vertex* from = dynamic_cast<OptimizableGraph::Vertex*>(*from_.begin()); | ||||
|     OptimizableGraph::Vertex* to = dynamic_cast<OptimizableGraph::Vertex*>(to_); | ||||
|     if (std::abs(from->id() - to->id()) != 1) // simple method to identify odometry edges in a pose graph
 | ||||
|       return std::numeric_limits<double>::max(); | ||||
|     SparseOptimizer::EdgeContainer::const_iterator it = _graph->findActiveEdge(e); | ||||
|     if (it == _graph->activeEdges().end()) // it has to be an active edge
 | ||||
|       return std::numeric_limits<double>::max(); | ||||
|     return e->initialEstimatePossible(from_, to); | ||||
|   } | ||||
| 
 | ||||
| } // end namespace
 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
							
								
								
									
										175
									
								
								SLAM/Thirdparty/g2o/g2o/core/estimate_propagator.h
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										175
									
								
								SLAM/Thirdparty/g2o/g2o/core/estimate_propagator.h
									
									
									
									
										vendored
									
									
								
							| @ -1,175 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 R. Kuemmerle, G. Grisetti, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| #ifndef G2O_ESTIMATE_PROPAGATOR_H | ||||
| #define G2O_ESTIMATE_PROPAGATOR_H | ||||
| 
 | ||||
| #include "optimizable_graph.h" | ||||
| #include "sparse_optimizer.h" | ||||
| 
 | ||||
| #include <map> | ||||
| #include <set> | ||||
| #include <limits> | ||||
| 
 | ||||
| #ifdef _MSC_VER | ||||
| #include <unordered_map> | ||||
| #else | ||||
| #include <tr1/unordered_map> | ||||
| #endif | ||||
| 
 | ||||
| namespace g2o { | ||||
| 
 | ||||
|   /**
 | ||||
|    * \brief cost for traversing along active edges in the optimizer | ||||
|    * | ||||
|    * You may derive an own one, if necessary. The default is to return initialEstimatePossible(from, to) for the edge. | ||||
|    */ | ||||
|   class  EstimatePropagatorCost { | ||||
|     public: | ||||
|       EstimatePropagatorCost (SparseOptimizer* graph); | ||||
|       virtual double operator()(OptimizableGraph::Edge* edge, const OptimizableGraph::VertexSet& from, OptimizableGraph::Vertex* to_) const; | ||||
|       virtual const char* name() const { return "spanning tree";} | ||||
|     protected: | ||||
|       SparseOptimizer* _graph; | ||||
|   }; | ||||
| 
 | ||||
|   /**
 | ||||
|    * \brief cost for traversing only odometry edges. | ||||
|    * | ||||
|    * Initialize your graph along odometry edges. An odometry edge is assumed to connect vertices | ||||
|    * whose IDs only differs by one. | ||||
|    */ | ||||
|   class  EstimatePropagatorCostOdometry : public EstimatePropagatorCost { | ||||
|     public: | ||||
|       EstimatePropagatorCostOdometry(SparseOptimizer* graph); | ||||
|       virtual double operator()(OptimizableGraph::Edge* edge, const OptimizableGraph::VertexSet& from_, OptimizableGraph::Vertex* to_) const; | ||||
|       virtual const char* name() const { return "odometry";} | ||||
|   }; | ||||
| 
 | ||||
|   /**
 | ||||
|    * \brief propagation of an initial guess | ||||
|    */ | ||||
|   class  EstimatePropagator { | ||||
|     public: | ||||
| 
 | ||||
|       /**
 | ||||
|        * \brief Applying the action for propagating. | ||||
|        * | ||||
|        * You may derive an own one, if necessary. The default is to call initialEstimate(from, to) for the edge. | ||||
|        */ | ||||
|       struct PropagateAction { | ||||
|         virtual void operator()(OptimizableGraph::Edge* e, const OptimizableGraph::VertexSet& from, OptimizableGraph::Vertex* to) const | ||||
|         { | ||||
|           if (! to->fixed()) | ||||
|             e->initialEstimate(from, to); | ||||
|         } | ||||
|       }; | ||||
| 
 | ||||
|       typedef EstimatePropagatorCost PropagateCost; | ||||
| 
 | ||||
|       class AdjacencyMapEntry; | ||||
| 
 | ||||
|       /**
 | ||||
|        * \brief priority queue for AdjacencyMapEntry | ||||
|        */ | ||||
|       class PriorityQueue : public std::multimap<double, AdjacencyMapEntry*> { | ||||
|         public: | ||||
|           void push(AdjacencyMapEntry* entry); | ||||
|           AdjacencyMapEntry* pop(); | ||||
|       }; | ||||
| 
 | ||||
|       /**
 | ||||
|        * \brief data structure for loopuk during Dijkstra | ||||
|        */ | ||||
|       class AdjacencyMapEntry { | ||||
|         public: | ||||
|           friend class EstimatePropagator; | ||||
|           friend class PriorityQueue; | ||||
|           AdjacencyMapEntry(); | ||||
|           void reset(); | ||||
|           OptimizableGraph::Vertex* child() const {return _child;} | ||||
|           const OptimizableGraph::VertexSet& parent() const {return _parent;} | ||||
|           OptimizableGraph::Edge* edge() const {return _edge;} | ||||
|           double distance() const {return _distance;} | ||||
|           int frontierLevel() const { return _frontierLevel;} | ||||
| 
 | ||||
|         protected: | ||||
|           OptimizableGraph::Vertex* _child; | ||||
|           OptimizableGraph::VertexSet _parent; | ||||
|           OptimizableGraph::Edge* _edge; | ||||
|           double _distance; | ||||
|           int _frontierLevel; | ||||
|         private: // for PriorityQueue
 | ||||
|           bool inQueue; | ||||
|           PriorityQueue::iterator queueIt; | ||||
|       }; | ||||
| 
 | ||||
|       /**
 | ||||
|        * \brief hash function for a vertex | ||||
|        */ | ||||
|       class VertexIDHashFunction { | ||||
|         public: | ||||
|           size_t operator ()(const OptimizableGraph::Vertex* v) const { return v->id();} | ||||
|       }; | ||||
| 
 | ||||
|       typedef std::tr1::unordered_map<OptimizableGraph::Vertex*, AdjacencyMapEntry, VertexIDHashFunction> AdjacencyMap; | ||||
| 
 | ||||
|     public: | ||||
|       EstimatePropagator(OptimizableGraph* g); | ||||
|       OptimizableGraph::VertexSet& visited() {return _visited; } | ||||
|       AdjacencyMap& adjacencyMap() {return _adjacencyMap; } | ||||
|       OptimizableGraph* graph() {return _graph;}  | ||||
| 
 | ||||
|       /**
 | ||||
|        * propagate an initial guess starting from v. The function computes a spanning tree | ||||
|        * whereas the cost for each edge is determined by calling cost() and the action applied to | ||||
|        * each vertex is action(). | ||||
|        */ | ||||
|       void propagate(OptimizableGraph::Vertex* v,  | ||||
|           const EstimatePropagator::PropagateCost& cost,  | ||||
|           const EstimatePropagator::PropagateAction& action = PropagateAction(), | ||||
|           double maxDistance=std::numeric_limits<double>::max(),  | ||||
|           double maxEdgeCost=std::numeric_limits<double>::max()); | ||||
| 
 | ||||
|       /**
 | ||||
|        * same as above but starting to propagate from a set of vertices instead of just a single one. | ||||
|        */ | ||||
|       void propagate(OptimizableGraph::VertexSet& vset,  | ||||
|           const EstimatePropagator::PropagateCost& cost,  | ||||
|           const EstimatePropagator::PropagateAction& action = PropagateAction(), | ||||
|           double maxDistance=std::numeric_limits<double>::max(),  | ||||
|           double maxEdgeCost=std::numeric_limits<double>::max()); | ||||
| 
 | ||||
|     protected: | ||||
|       void reset(); | ||||
| 
 | ||||
|       AdjacencyMap _adjacencyMap; | ||||
|       OptimizableGraph::VertexSet _visited; | ||||
|       OptimizableGraph* _graph; | ||||
|   }; | ||||
| 
 | ||||
| } | ||||
| #endif | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
| @ -1,2 +0,0 @@ | ||||
| [ZoneTransfer] | ||||
| ZoneId=3 | ||||
							
								
								
									
										217
									
								
								SLAM/Thirdparty/g2o/g2o/core/factory.cpp
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										217
									
								
								SLAM/Thirdparty/g2o/g2o/core/factory.cpp
									
									
									
									
										vendored
									
									
								
							| @ -1,217 +0,0 @@ | ||||
| // g2o - General Graph Optimization
 | ||||
| // Copyright (C) 2011 R. Kuemmerle, G. Grisetti, W. Burgard
 | ||||
| // All rights reserved.
 | ||||
| //
 | ||||
| // Redistribution and use in source and binary forms, with or without
 | ||||
| // modification, are permitted provided that the following conditions are
 | ||||
| // met:
 | ||||
| //
 | ||||
| // * Redistributions of source code must retain the above copyright notice,
 | ||||
| //   this list of conditions and the following disclaimer.
 | ||||
| // * Redistributions in binary form must reproduce the above copyright
 | ||||
| //   notice, this list of conditions and the following disclaimer in the
 | ||||
| //   documentation and/or other materials provided with the distribution.
 | ||||
| //
 | ||||
| // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 | ||||
| // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 | ||||
| // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 | ||||
| // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 | ||||
| // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
 | ||||
| // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 | ||||
| // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 | ||||
| // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 | ||||
| // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 | ||||
| // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | ||||
| 
 | ||||
| #include "factory.h" | ||||
| 
 | ||||
| #include "creators.h" | ||||
| #include "parameter.h" | ||||
| #include "cache.h" | ||||
| #include "optimizable_graph.h" | ||||
| #include "../stuff/color_macros.h" | ||||
| 
 | ||||
| #include <iostream> | ||||
| #include <typeinfo> | ||||
| #include <cassert> | ||||
| 
 | ||||
| using namespace std; | ||||
| 
 | ||||
| namespace g2o { | ||||
| 
 | ||||
| Factory* Factory::factoryInstance = 0; | ||||
| 
 | ||||
| Factory::Factory() | ||||
| { | ||||
| } | ||||
| 
 | ||||
| Factory::~Factory() | ||||
| { | ||||
| # ifdef G2O_DEBUG_FACTORY | ||||
|   cerr << "# Factory destroying " << (void*)this << endl; | ||||
| # endif | ||||
|   for (CreatorMap::iterator it = _creator.begin(); it != _creator.end(); ++it) { | ||||
|     delete it->second->creator; | ||||
|   } | ||||
|   _creator.clear(); | ||||
|   _tagLookup.clear(); | ||||
| } | ||||
| 
 | ||||
| Factory* Factory::instance() | ||||
| { | ||||
|   if (factoryInstance == 0) { | ||||
|     factoryInstance = new Factory; | ||||
| #  ifdef G2O_DEBUG_FACTORY | ||||
|     cerr << "# Factory allocated " << (void*)factoryInstance << endl; | ||||
| #  endif | ||||
|   } | ||||
| 
 | ||||
|   return factoryInstance; | ||||
| } | ||||
| 
 | ||||
| void Factory::registerType(const std::string& tag, AbstractHyperGraphElementCreator* c) | ||||
| { | ||||
|   CreatorMap::const_iterator foundIt = _creator.find(tag); | ||||
|   if (foundIt != _creator.end()) { | ||||
|     cerr << "FACTORY WARNING: Overwriting Vertex tag " << tag << endl; | ||||
|     assert(0); | ||||
|   } | ||||
|   TagLookup::const_iterator tagIt = _tagLookup.find(c->name()); | ||||
|   if (tagIt != _tagLookup.end()) { | ||||
|     cerr << "FACTORY WARNING: Registering same class for two tags " << c->name() << endl; | ||||
|     assert(0); | ||||
|   } | ||||
| 
 | ||||
|   CreatorInformation* ci = new CreatorInformation(); | ||||
|   ci->creator = c; | ||||
| 
 | ||||
| #ifdef G2O_DEBUG_FACTORY | ||||
|   cerr << "# Factory " << (void*)this << " constructing type " << tag << " "; | ||||
| #endif | ||||
|   // construct an element once to figure out its type
 | ||||
|   HyperGraph::HyperGraphElement* element = c->construct(); | ||||
|   ci->elementTypeBit = element->elementType(); | ||||
| 
 | ||||
| #ifdef G2O_DEBUG_FACTORY | ||||
|   cerr << "done." << endl; | ||||
|   cerr << "# Factory " << (void*)this << " registering " << tag; | ||||
|   cerr << " " << (void*) c << " "; | ||||
|   switch (element->elementType()) { | ||||
|     case HyperGraph::HGET_VERTEX: | ||||
|       cerr << " -> Vertex"; | ||||
|       break; | ||||
|     case HyperGraph::HGET_EDGE: | ||||
|       cerr << " -> Edge"; | ||||
|       break; | ||||
|     case HyperGraph::HGET_PARAMETER: | ||||
|       cerr << " -> Parameter"; | ||||
|       break; | ||||
|     case HyperGraph::HGET_CACHE: | ||||
|       cerr << " -> Cache"; | ||||
|       break; | ||||
|     case HyperGraph::HGET_DATA: | ||||
|       cerr << " -> Data"; | ||||
|       break; | ||||
|     default: | ||||
|       assert(0 && "Unknown element type occured, fix elementTypes"); | ||||
|       break; | ||||
|   } | ||||
|   cerr << endl; | ||||
| #endif | ||||
| 
 | ||||
|   _creator[tag] = ci; | ||||
|   _tagLookup[c->name()] = tag; | ||||
|   delete element; | ||||
| } | ||||
| 
 | ||||
|   void Factory::unregisterType(const std::string& tag) | ||||
|   { | ||||
|     // Look for the tag
 | ||||
|     CreatorMap::iterator tagPosition = _creator.find(tag); | ||||
| 
 | ||||
|     if (tagPosition != _creator.end()) { | ||||
| 
 | ||||
|       AbstractHyperGraphElementCreator* c = tagPosition->second->creator; | ||||
| 
 | ||||
|       // If we found it, remove the creator from the tag lookup map
 | ||||
|       TagLookup::iterator classPosition = _tagLookup.find(c->name()); | ||||
|       if (classPosition != _tagLookup.end()) | ||||
|         { | ||||
|           _tagLookup.erase(classPosition); | ||||
|         } | ||||
|       _creator.erase(tagPosition); | ||||
|     } | ||||
|   } | ||||
| 
 | ||||
| HyperGraph::HyperGraphElement* Factory::construct(const std::string& tag) const | ||||
| { | ||||
|   CreatorMap::const_iterator foundIt = _creator.find(tag); | ||||
|   if (foundIt != _creator.end()) { | ||||
|     //cerr << "tag " << tag << " -> " << (void*) foundIt->second->creator << " " << foundIt->second->creator->name() << endl;
 | ||||
|     return foundIt->second->creator->construct(); | ||||
|   } | ||||
|   return 0; | ||||
| } | ||||
| 
 | ||||
| const std::string& Factory::tag(const HyperGraph::HyperGraphElement* e) const | ||||
| { | ||||
|   static std::string emptyStr(""); | ||||
|   TagLookup::const_iterator foundIt = _tagLookup.find(typeid(*e).name()); | ||||
|   if (foundIt != _tagLookup.end()) | ||||
|     return foundIt->second; | ||||
|   return emptyStr; | ||||
| } | ||||
| 
 | ||||
| void Factory::fillKnownTypes(std::vector<std::string>& types) const | ||||
| { | ||||
|   types.clear(); | ||||
|   for (CreatorMap::const_iterator it = _creator.begin(); it != _creator.end(); ++it) | ||||
|     types.push_back(it->first); | ||||
| } | ||||
| 
 | ||||
| bool Factory::knowsTag(const std::string& tag, int* elementType) const | ||||
| { | ||||
|   CreatorMap::const_iterator foundIt = _creator.find(tag); | ||||
|   if (foundIt == _creator.end()) { | ||||
|     if (elementType) | ||||
|       *elementType = -1; | ||||
|     return false; | ||||
|   } | ||||
|   if (elementType) | ||||
|     *elementType = foundIt->second->elementTypeBit; | ||||
|   return true; | ||||
| } | ||||
| 
 | ||||
| void Factory::destroy() | ||||
| { | ||||
|   delete factoryInstance; | ||||
|   factoryInstance = 0; | ||||
| } | ||||
| 
 | ||||
| void Factory::printRegisteredTypes(std::ostream& os, bool comment) const | ||||
| { | ||||
|   if (comment) | ||||
|     os << "# "; | ||||
|   os << "types:" << endl; | ||||
|   for (CreatorMap::const_iterator it = _creator.begin(); it != _creator.end(); ++it) { | ||||
|     if (comment) | ||||
|       os << "#"; | ||||
|     cerr << "\t" << it->first << endl; | ||||
|   } | ||||
| } | ||||
| 
 | ||||
| HyperGraph::HyperGraphElement* Factory::construct(const std::string& tag, const HyperGraph::GraphElemBitset& elemsToConstruct) const | ||||
| { | ||||
|   if (elemsToConstruct.none()) { | ||||
|     return construct(tag); | ||||
|   } | ||||
|   CreatorMap::const_iterator foundIt = _creator.find(tag); | ||||
|   if (foundIt != _creator.end() && foundIt->second->elementTypeBit >= 0 && elemsToConstruct.test(foundIt->second->elementTypeBit)) { | ||||
|     return foundIt->second->creator->construct(); | ||||
|   } | ||||
|   return 0; | ||||
| } | ||||
| 
 | ||||
| } // end namespace
 | ||||
| 
 | ||||
Some files were not shown because too many files have changed in this diff Show More
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user