9

CMakeLists.txt文件如何编写?(一 基础篇)

 3 years ago
source link: https://mp.weixin.qq.com/s/eyQQgteL4XGAUYCy9HB_Mw
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.

点击上方“3D视觉工坊”,选择“星标”

干货第一时间送达

3D视觉工坊的第62篇文章

本文以linux平台下CMakeLists.txt文件书写方法总结。

一 开头通用模块

1.1 cmake版本要求

cmake_minimum_required( VERSION 2.8 )

#工程文件名loop_closure,可任取

project( loop_closure )

1.2 编译模式

IF(NOT CMAKE_BUILD_TYPE)
 SET(CMAKE_BUILD_TYPE Release)
ENDIF()

MESSAGE("Build type: " ${CMAKE_BUILD_TYPE})

当然如果此处在前面加上语句:

set(CMAKE_BUILD_TYPE debug)

即表示设置为debug模式编译。

1.3 检查C++版本

检查C++的版本

# Check C++11 or C++0x supportinclude(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()

二 项目文件配置模块

接下来,便开始配置各个库模块。

2.1 如果仅包含OpenCV库时

set(OpenCV_DIR "/usr/local/include/opencv3.2.0/share/OpenCV")
find_package(OpenCV REQUIRED)

include_directories( ${OpenCV_INCLUDE_DIRS} )

#生成可执行文件

add_executable(${PROJECT_NAME} src/loop_closure.cpp )

target_link_libraries(${PROJECT_NAME} ${OpenCV_LIBS})

备注:这里的OpenCV包含目录为含有OpenCVConfig.cmake的路径。

640
640

2.2 如果包含第三方库,该库为源码形式(.h和.cpp),非动态链接库

640

此处以在工程中添加词袋库DBoW2为例,这里的DBoW2是以源码形式包含,也即未编译成.so文件。

640
 

2.2.1 包含第三库的头文件

#设置.h文件对应的路径

set( DBoW2_INCLUDE_DIRS ${PROJECT_SOURCE_DIR}/ThirdParty/DBow-master/include/)

#包含.h文件路径

include_directories( ${OpenCV_INCLUDE_DIRS}         ${DBoW2_INCLUDE_DIRS} ${DBoW2_INCLUDE_DIRS}/DBoW2/)

注:上述为啥要用两条路径${DBoW2_INCLUDE_DIRS}和${DBoW2_INCLUDE_DIRS}/DBoW2/?

640

 

640

为了防止在include层找不到,继续往下一层路径include/DBoW2/路径下查找,这是为了防止某些文件的包含路径不一致导致头文件查找错误。

2.2.2 包含第三方库的cpp文件

640
640
 

set(DBoW2_SRCS "${PROJECT_SOURCE_DIR}/ThirdParty/DBow-master/src")

#生成可执行文件

add_executable(${PROJECT_NAME} src/loop_closure.cpp  src/run_main.cpp${DBoW2_SRCS}/BowVector.cpp ${DBoW2_SRCS}/FBrief.cpp ${DBoW2_SRCS}/FeatureVector.cpp${DBoW2_SRCS}/FORB.cpp ${DBoW2_SRCS}/FSurf64.cpp ${DBoW2_SRCS}/QueryResults.cpp ${DBoW2_SRCS}/ScoringObject.cpp)

其中,src/loop_closure.cpp  src/run_main.cpp 为本工程中我自己实现的,而对于其他的cpp文件,则直接添加路径即可。

另一种方式,添加cpp文件路径更为简洁方便。

file(GLOB DBoW2_SRCS ${PROJECT_SOURCE_DIR}/ThirdParty/DBow-master/src/*.cpp)

add_executable(${PROJECT_NAME} src/loop_closure.cpp  src/run_main.cpp${DBoW2_SRCS})

2.3 如果包含第三方库,为库形式(此处以静态库为例(.a后缀))

在上述工程下,同时还包含有DBoW3库,此库已经按默认路径编译安装到计算机内存中。我们可以按如下方式添加DBoW3库。

1)包含头文件

set( DBoW3_INCLUDE_DIRS "/usr/local/include")

2)添加库

set( DBoW3_LIBS "/usr/local/lib/libDBoW3.a")

target_link_libraries(${PROJECT_NAME}${OpenCV_LIBS}${DBoW3_LIBS})

通过上述方式,即可调用。

三 一个简单的CMakeLists.txt文件demo

该demo中相较于上述总结添加的库,还额外包含了DLib库。

cmake_minimum_required( VERSION 2.8 )
project( loop_closure )

#set(CMAKE_BUILD_TYPE  Debug)IF(NOT CMAKE_BUILD_TYPE)
  SET(CMAKE_BUILD_TYPE Release)
ENDIF()

MESSAGE("Build type: " ${CMAKE_BUILD_TYPE})
# Check C++11 or C++0x supportinclude(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()

#opencv#set(OpenCV_DIR "/usr/local/include/opencv3.2.0/share/OpenCV")set(OpenCV_DIR "/opt/ros/kinetic/share/OpenCV-3.3.1-dev")

find_package(OpenCV REQUIRED)

set( DBoW3_INCLUDE_DIRS "/usr/local/include")

set( DBoW2_INCLUDE_DIRS ${PROJECT_SOURCE_DIR}/ThirdParty/DBow-master/include/)
message(${DBoW2_INCLUDE_DIRS})

#important#file(GLOB DBoW2_SRCS ${PROJECT_SOURCE_DIR}/ThirdParty/DBow-master/src/*.cpp)#message(${DBoW2_SRCS})set(DBoW2_SRCS "${PROJECT_SOURCE_DIR}/ThirdParty/DBow-master/src")
message(${DBoW2_SRCS})

find_package(DLib QUIET        PATHS ${DEPENDENCY_INSTALL_DIR})
if(${DLib_FOUND})
   message("DLib library found, using it from the system")
   include_directories(${DLib_INCLUDE_DIRS})
   add_custom_target(Dependencies)
else(${DLib_FOUND})
   message("DLib library not found in the system, it will be downloaded on build")
   option(DOWNLOAD_DLib_dependency "Download DLib dependency" ON)
   if(${DOWNLOAD_DLib_dependency})
      ExternalProject_Add(DLib              PREFIX ${DEPENDENCY_DIR}GIT_REPOSITORY http://github.com/dorian3d/DLib              GIT_TAG master              INSTALL_DIR ${DEPENDENCY_INSTALL_DIR}CMAKE_ARGS -DCMAKE_INSTALL_PREFIX=<INSTALL_DIR>)
      add_custom_target(Dependencies ${CMAKE_COMMAND} ${CMAKE_SOURCE_DIR} DEPENDS DLib)
   else()
      message(SEND_ERROR "Please, activate DOWNLOAD_DLib_dependency option or download manually")
   endif(${DOWNLOAD_DLib_dependency})
endif(${DLib_FOUND})

include_directories( ${OpenCV_INCLUDE_DIRS}        ${DBoW3_INCLUDE_DIRS} ${DBoW2_INCLUDE_DIRS} ${DBoW2_INCLUDE_DIRS}/DBoW2/)

message("DBoW3_INCLUDE_DIRS ${DBoW3_INCLUDE_DIRS}")
message("DBoW2_INCLUDE_DIRS ${DBoW2_INCLUDE_DIRS}")

message("opencv ${OpenCV_VERSION}")

# dbow3 # dbow3 is a simple lib so I assume you installed it in default directoryset( DBoW3_LIBS "/usr/local/lib/libDBoW3.a")

add_executable(${PROJECT_NAME} src/loop_closure.cpp  src/run_main.cpp${DBoW2_SRCS}/BowVector.cpp ${DBoW2_SRCS}/FBrief.cpp ${DBoW2_SRCS}/FeatureVector.cpp${DBoW2_SRCS}/FORB.cpp ${DBoW2_SRCS}/FSurf64.cpp ${DBoW2_SRCS}/QueryResults.cpp ${DBoW2_SRCS}/ScoringObject.cpp)
message(${DBoW2_SRCS}/BowVector.cpp)

target_link_libraries(${PROJECT_NAME}${OpenCV_LIBS}

${DLib_LIBS}${DBoW3_LIBS})

四 跋

以上仅仅为CMakeLists.txt的一个简单用法梳理,如有不到之处,还请批评指正。对于大型工程的管理,还有很多学问可以挖掘,此处限于篇幅便不再展示,欢迎加入我们的学习圈「3D视觉技术」进一步探讨、交流、学习。

学习3D视觉核心技术,扫描查看介绍,3天内无条件退款

640

 圈里有高质量教程资料、可答疑解惑、助你高效解决问题


About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK