webentwicklung-frage-antwort-db.com.de

Wie fügt man Boost-Bibliotheken in CMakeLists.txt hinzu?

Ich muss Boost-Bibliotheken in meine CMakeLists.txt einfügen. Wie machst du das oder wie fügst du es hinzu?

108
laksh

Gib das in dein CMakeLists.txt Datei (ändern Sie die Optionen von AUS nach EIN, wenn Sie möchten):

set(Boost_USE_STATIC_LIBS OFF) 
set(Boost_USE_MULTITHREADED ON)  
set(Boost_USE_STATIC_RUNTIME OFF) 
find_package(Boost 1.45.0 COMPONENTS *boost libraries here*) 

if(Boost_FOUND)
    include_directories(${Boost_INCLUDE_DIRS}) 
    add_executable(progname file1.cxx file2.cxx) 
    target_link_libraries(progname ${Boost_LIBRARIES})
endif()

Offensichtlich müssen Sie die gewünschten Bibliotheken dort ablegen, wo ich *boost libraries here*. Wenn Sie beispielsweise die Bibliothek filesystem und regex verwenden, schreiben Sie:

find_package(Boost 1.45.0 COMPONENTS filesystem regex)
157
LainIwakura

Sie können find_package verwenden, um nach verfügbaren Boost-Bibliotheken zu suchen. Die Suche nach Boost wird auf FindBoost.cmake verschoben, das standardmäßig mit CMake installiert wird.

Beim Auffinden von Boost hat der Aufruf find_package() viele Variablen gefüllt (überprüfen Sie die Referenz auf FindBoost.cmake ). Darunter befinden sich die Variablen BOOST_INCLUDE_DIRS, Boost_LIBRARIES und Boost_XXX_LIBRARY, wobei XXX durch bestimmte Boost-Bibliotheken ersetzt wurde. Mit diesen können Sie include_directories und target_link_libraries angeben.

Angenommen, Sie würden boost :: program_options und boost :: regex benötigen, dann würden Sie Folgendes tun:

find_package( Boost REQUIRED COMPONENTS program_options regex )
include_directories( ${Boost_INCLUDE_DIRS} )
add_executable( run main.cpp ) # Example application based on main.cpp

# Alternatively you could use ${Boost_LIBRARIES} here.
target_link_libraries( run ${Boost_PROGRAM_OPTIONS_LIBRARY} ${Boost_REGEX_LIBRARY} )

Einige allgemeine Tipps:

  • Bei der Suche überprüft FindBoost die Umgebungsvariable $ ENV {BOOST_ROOT}. Sie können diese Variable bei Bedarf vor dem Aufruf von find_package setzen.
  • Wenn Sie mehrere Build-Versionen von boost haben (Multithread, Static, Shared usw.), können Sie die gewünschte Konfiguration angeben, bevor Sie find_package aufrufen. Setzen Sie dazu einige der folgenden Variablen auf On: Boost_USE_STATIC_LIBS, Boost_USE_MULTITHREADED, Boost_USE_STATIC_RUNTIME
  • Achten Sie bei der Suche nach Boost unter Windows auf die automatische Verknüpfung. Lesen Sie den "HINWEIS für Visual Studio-Benutzer" in Referenz .
    • Mein Rat ist, die automatische Verknüpfung zu deaktivieren und cmakes Abhängigkeitsbehandlung zu verwenden: add_definitions( -DBOOST_ALL_NO_LIB )
    • In einigen Fällen müssen Sie möglicherweise explizit angeben, dass ein dynamischer Boost verwendet wird: add_definitions( -DBOOST_ALL_DYN_LINK )
73
André

Angepasst an @ LainIwakuras Antwort auf die moderne CMake-Syntax mit importierten Zielen wäre dies:

set(Boost_USE_STATIC_LIBS OFF) 
set(Boost_USE_MULTITHREADED ON)  
set(Boost_USE_STATIC_RUNTIME OFF) 
find_package(Boost 1.45.0 COMPONENTS filesystem regex) 

if(Boost_FOUND)
    add_executable(progname file1.cxx file2.cxx) 
    target_link_libraries(progname Boost::filesystem Boost::regex)
endif()

Beachten Sie, dass die Include-Verzeichnisse nicht mehr manuell angegeben werden müssen, da dies bereits über die importierten Ziele Boost::filesystem Und Boost::regex Erledigt wird.
regex und filesystem können durch alle benötigten Boost-Bibliotheken ersetzt werden.

20
oLen

Möge dies für manche Menschen hilfreich sein. Ich hatte einen bösen Fehler: ndefinierter Verweis auf das Symbol '_ZN5boost6system15system_categoryEv' //usr/lib/x86_64-linux-gnu/libboost_system.so.1.58.0: Fehler beim Hinzufügen von Symbolen: DSO fehlt in der Befehlszeile Dort Es gab ein Problem mit cmakeList.txt, und irgendwie fehlte mir, die Bibliotheken "system" und "filesystem" explizit einzuschließen. Also habe ich diese Zeilen in CMakeLists.txt geschrieben

Diese Zeilen werden zu Beginn geschrieben, bevor die ausführbare Datei des Projekts erstellt wird, da zu diesem Zeitpunkt keine Verknüpfung der Boost-Bibliothek mit der ausführbaren Datei des Projekts erforderlich ist.

set(Boost_USE_STATIC_LIBS OFF) 
set(Boost_USE_MULTITHREADED ON)  
set(Boost_USE_STATIC_RUNTIME OFF) 
set(Boost_NO_SYSTEM_PATHS TRUE) 

if (Boost_NO_SYSTEM_PATHS)
  set(BOOST_ROOT "${CMAKE_CURRENT_SOURCE_DIR}/../../3p/boost")
  set(BOOST_INCLUDE_DIRS "${BOOST_ROOT}/include")
  set(BOOST_LIBRARY_DIRS "${BOOST_ROOT}/lib")
endif (Boost_NO_SYSTEM_PATHS)


find_package(Boost COMPONENTS regex date_time system filesystem thread graph program_options) 

find_package(Boost REQUIRED regex date_time system filesystem thread graph program_options)
find_package(Boost COMPONENTS program_options REQUIRED)

Jetzt am Ende der Datei habe ich diese Zeilen geschrieben, indem ich "KeyPointEvaluation" als mein ausführbares Projekt betrachtete.

if(Boost_FOUND)
    include_directories(${BOOST_INCLUDE_DIRS})
    link_directories(${Boost_LIBRARY_DIRS})
    add_definitions(${Boost_DEFINITIONS})

    include_directories(${Boost_INCLUDE_DIRS})  
    target_link_libraries(KeyPointEvaluation ${Boost_LIBRARIES})
    target_link_libraries( KeyPointEvaluation ${Boost_PROGRAM_OPTIONS_LIBRARY} ${Boost_FILESYSTEM_LIBRARY} ${Boost_REGEX_LIBRARY} ${Boost_SYSTEM_LIBRARY})
endif()
6
Spandan

Ich stimme den Antworten 1 und 2 zu. Ich bevorzuge es jedoch, jede Bibliothek separat anzugeben. Dies macht die Abhängigkeiten in großen Projekten klarer. Es besteht jedoch die Gefahr, dass die (Groß- und Kleinschreibung berücksichtigenden) Variablennamen falsch eingegeben werden. In diesem Fall liegt kein direkter cmake-Fehler vor, aber einige undefinierte Verweislinkerprobleme, deren Behebung einige Zeit in Anspruch nehmen kann. Deshalb benutze ich folgende cmake-Funktion:

function(VerifyVarDefined)
  foreach(lib ${ARGV}) 
    if(DEFINED ${lib})
    else(DEFINED ${lib})
      message(SEND_ERROR "Variable ${lib} is not defined")
    endif(DEFINED ${lib})
  endforeach()
endfunction(VerifyVarDefined)

Für das oben erwähnte Beispiel sieht das so aus:

VerifyVarDefined(Boost_PROGRAM_OPTIONS_LIBRARY Boost_REGEX_LIBRARY)
target_link_libraries( run ${Boost_PROGRAM_OPTIONS_LIBRARY} ${Boost_REGEX_LIBRARY} )

Wenn ich "BOOST_PROGRAM_OPTIONS_LIBRARY" geschrieben hätte, wäre ein Fehler aufgetreten, der von cmake und nicht viel später vom Linker ausgelöst wurde.

2
MarkusParker

Versuchen Sie es mit Boost-Dokumentation :

set(Boost_USE_STATIC_LIBS        ON)  # only find static libs
set(Boost_USE_DEBUG_LIBS         OFF) # ignore debug libs and 
set(Boost_USE_RELEASE_LIBS       ON)  # only find release libs 
set(Boost_USE_MULTITHREADED      ON)
set(Boost_USE_STATIC_RUNTIME    OFF) 
find_package(Boost 1.66.0 COMPONENTS date_time filesystem system ...)
if(Boost_FOUND)   
    include_directories(${Boost_INCLUDE_DIRS})
    add_executable(foo foo.cc)   
    target_link_libraries(foo ${Boost_LIBRARIES})
endif()

Vergessen Sie nicht, foo durch Ihren Projektnamen und Komponenten durch Ihre zu ersetzen!

1
Nikolay Pakudin