C/C++包管理工具:Conan

Conan是一個專為C/C++設計的開源、去中心化、跨平臺的包管理器,致力于簡化依賴管理和二進制分發流程。Conan基于Python進行開發,支持與主流的構建系統集成,提供了強大的跨平臺和交叉編譯能力。通過Conan,開發者可以高效的創建、共享和使用預編譯的二進制包,提升開發效率和協作體驗,尤其適合于復雜項目和多環境部署的場景。

下文將結合一個cmake構建系統的C++ Demo工程介紹conan安裝、基本概念及簡單使用,更多的示例和更復雜的應用需求建議查詢Conan用戶文檔。

Conan用戶文檔:https://docs.conan.io/2/index.html

一、安裝

pipx install conan

驗證安裝結果:

$ conan -v
Conan version 2.20.0

Conan1.x和Conan2.x不兼容,默認是conan2.x,如果使用Conan1.x可以指定版本安裝

pipx install conan==1.66.0

二、概念和配置

1、常用命令(commands)
  • conan config: 管理conan的配置(遠程、設置、插件等)
    # 指定目錄安裝conan配置文件: 
    conan config install <config_path> 
    
  • conan profile: 顯示和管理profile文件
    # 查看所有的profile文件
    conan profile list
    
  • conan remove: 移除包從本地緩存或遠程
    # 移除指定的包
    conan remove <name>
    # 移除指定版本的包
    conan remove <name>/<version>
    
  • conan version: 查看conan客戶端的版本信息
    $ conan version
    version: 2.20.0
    conan_path: /root/.local/bin/conan
    pythonversion: 3.12.3sys_version: 3.12.3 (main, Aug 14 2025, 17:47:21) [GCC 13.3.0]sys_executable: /root/.local/share/pipx/venvs/conan/bin/pythonis_frozen: Falsearchitecture: x86_64
    systemversion: #149~20.04.1-Ubuntu SMP Wed Apr 16 08:29:56 UTC 2025platform: Linux-5.15.0-139-generic-x86_64-with-glibc2.39system: Linuxrelease: 5.15.0-139-genericcpu: x86_64
    
  • conan create: 從一個配方文件創建一個包
    # 當二進制不存在時構建
    conan create <project_path> -pr=<profile_file> --build=missing
    
2、配方文件(conanfile.py)

conanfile.py是一個包的配方,負責定義怎么定義和消費一個包。

from conan import ConanFileclass HelloConan(ConanFile):...

conanfile.py使用了多種屬性(attributes)和方法(methods)用于操作。為了避免沖突,請遵循一下規則:

  • 公共屬性和方法,像build(),self.package_folder,是conan保留的。不要在配方中使用這些公共成員作為自定義屬性或方法。
  • 對你自己的成員使用“protected”訪問,像self._my_data或def _my_helper(self):。Conan只保留“_conan”作為保護成員的開始。
(1)屬性(attributes)

conanfile.py Attributes文檔:https://docs.conan.io/2/reference/conanfile/attributes.html

Attribute說明
name包的名字
version包的版本
description包的描述信息
license包的license信息
author包的作者信息
setting列舉第一層的配置信息(來自setting.yml),這些值將被用于計算package id
options定義option的名字及允許的值,默認任何值改變都將影響package id
default_options定義options的默認值
generators描述所需的生成器名字

注:Attribute一般提供簡單的功能,對于復雜的需求可以使用功能相似的Method實現。

(2)方法(methods)

conanfile.py Methods文檔:https://docs.conan.io/2/reference/conanfile/methods.html

Mathod說明
build()包含了從源碼構建包的構建指令
build_requirements()定義了tool_requirestest_requires
configure()允許在計算依賴時進行配置和選擇
deploy()從package中復制指定文件到特定目錄
generate()生成構建包時所必須的文件
layout()定義工程相關的源文件夾、build文件夾等
package()從build文件夾copy文件到package文件夾
requirements()定義依賴的包
set_name()動態定義包的名字
set_version()動態定義包的版本
system_requirements()調用系統包管理(比如apt)安裝系統包
test()運行簡單的包測試
(3)Running命令

對于系統命令,Conan提供了self.run()方法,支持在指定環境中運行相應的系統命令,并且當命令執行錯誤時,支持拋出異常以便錯誤能夠被及時發現。

run(self, command: str, stdout=None, cwd=None, ignore_errors=False, env='', quiet=False, shell=True, scope='build', stderr=None)
  • command – 待運行的命令字符串.
  • stdout – 支持將標準輸出重定向,默認輸出到標準輸出流。
  • stderr – 支持將錯誤輸出重定向,默認輸出到標準錯誤流。
  • cwd – 指定運行命令的工作空間。
  • ignore_errors – 如果為Ture,命令執行錯誤也將不拋出異常。
  • env – 要使用的環境文件,當scope為build時默認為conanbuild,否則scope為run默認使用conanrun。如果明確設置為None則不會使用任何環境文件。
  • quiet – 如果為True,將屏蔽該命令的輸出。
  • shell – 如果為True,將在一個shell中運行該命令。這將會被傳遞給底層的popen函數。
  • scope – 這個命令的范圍,只能是“build”或者“run”。用于指定命令執行時所處的環境作用域。它們決定了命令執行時使用的環境變量集合。(這些環境變量通常在generate()階段生成并保存在相應腳本中)
(4)從配方輸出文本

Conan建議使用self.output代替print()從配方中輸出文本信息。self.output下的成員方法有:

error(self, msg:str, error_type:str=None)
warning(self, msg:str, warn_tag:str=None)
info(self, msg:str, fg:str=None, bg:str=None)status(self, msg:str, fg:str=None, bg:str=None)
verbose(self, msg:str, fg:str=None, bg:str=None)
debug(self, msg:str, fg:str='\x1b[35m',bg:str=None)
trace(self, msg:str)success(self, msg:str)
highlight(self, msg:str)
(5)配方工具

配方工具文檔:https://docs.conan.io/2/reference/tools.html

配方工具是指能夠在conan配方中引用的工具,比如:

from conan.tools.cmake import CMakeToolchain, CMakeDeps, CMake, cmake_layout
from conan.tools.env import Environment, EnvVars, VirtualBuildEnv, VirtualRunEnv
from conan.tools.files import *
from conan.tools.scm import Git, Version
from conan.tools.system import Apt

注:conanfile.py還有一個對功能簡單的版本:conanfile.txt,便于對依賴項的簡單管理使用,不能用于創建軟件包。

3、配置文件
(1)global.conf

global.conf文件位于Conan的家目錄,~/.conan2/global.conf。如果不存在將自動創建一個。global.conf文件的目標是存在一些核心(core)、工具(tool)及用戶(user)的配置變量,這些變量也將會被Conan使用。

  • core.*:旨在配置 Conan 核心行為的參數(下載重試次數、包標識模式等)。僅能在global.conf文件中進行定義。
  • tool.*: 旨在配置 Conan 工具(工具鏈、構建輔助程序等)在您的配方中所使用的值。可在global.conf和配置文件中進行定義。
  • user.*: 旨在定義個人用戶配置。用戶可以自行設定任何所需內容。這些配置可在global.conf文件和配置文件中進行設定。

使用命令conan config list可以查看當前的所有配置。

(2)profiles

Conan配置文件允許用戶在文件中為設置、選項、環境變量(包括構建時和運行時環境)以及工具需求和配置變量設定一個完整的配置集。

[settings]
arch=x86_64
build_type=Release
os=Macos[options]
mylib/*:shared=True[tool_requires]
tool1/0.1@user/channel
*: tool4/0.1@user/channel[buildenv]
VAR1=value[runenv]
EnvironmentVar1=My Value[conf]
tools.build:jobs=2[replace_requires]
zlib/1.2.12: zlib/[*][replace_tool_requires]
7zip/*: 7zip/system[platform_requires]
dlib/1.3.22[platform_tool_requires]
cmake/3.24.2

注:對不需要特定設置section,可以不在profile中聲明。

(3)settings.yml
# This file was generated by Conan. Remove this comment if you edit this file or Conan
# will destroy your changes.
os:Windows:subsystem: [null, cygwin, msys, msys2, wsl]WindowsStore:version: ["8.1", "10.0"]WindowsCE:platform: [ANY]version: ["5.0", "6.0", "7.0", "8.0"]Linux:iOS:version: &ios_version["7.0", "7.1", "8.0", "8.1", "8.2", "8.3", "8.4", "9.0", "9.1", "9.2", "9.3","10.0", "10.1", "10.2", "10.3","11.0", "11.1", "11.2", "11.3", "11.4","12.0", "12.1", "12.2", "12.3", "12.4", "12.5","13.0", "13.1", "13.2", "13.3", "13.4", "13.5", "13.6", "13.7","14.0", "14.1", "14.2", "14.3", "14.4", "14.5", "14.6", "14.7", "14.8","15.0", "15.1", "15.2", "15.3", "15.4", "15.5", "15.6", "15.7", "15.8","16.0", "16.1", "16.2", "16.3", "16.4", "16.5", "16.6", "16.7","17.0", "17.1", "17.2", "17.3", "17.4", "17.5", "17.6", "17.8","18.0", "18.1", "18.2", "18.3", "18.4", "18.5", "18.6"]sdk: ["iphoneos", "iphonesimulator"]sdk_version: [null, "11.3", "11.4", "12.0", "12.1", "12.2", "12.4","13.0", "13.1", "13.2", "13.3", "13.4", "13.5", "13.6", "13.7","14.0", "14.1", "14.2", "14.3", "14.4", "14.5", "15.0", "15.2", "15.4","15.5", "16.0", "16.1", "16.2", "16.4", "17.0", "17.1", "17.2", "17.4", "17.5","18.0", "18.1", "18.2", "18.4", "18.5"]watchOS:version: ["4.0", "4.1", "4.2", "4.3", "5.0", "5.1", "5.2", "5.3", "6.0", "6.1", "6.2", "6.3","7.0", "7.1", "7.2", "7.3", "7.4", "7.5", "7.6","8.0", "8.1", "8.3", "8.4", "8.5", "8.6", "8.7","9.0","9.1", "9.2", "9.3", "9.4", "9.5", "9.6","10.0", "10.1", "10.2", "10.3", "10.4", "10.5", "10.6","11.0", "11.1", "11.2", "11.3", "11.4", "11.5", "11.6"]sdk: ["watchos", "watchsimulator"]sdk_version: [null, "4.3", "5.0", "5.1", "5.2", "5.3", "6.0", "6.1", "6.2","7.0", "7.1", "7.2", "7.3", "7.4", "8.0", "8.0.1", "8.3", "8.5", "9.0", "9.1","9.4", "10.0", "10.1", "10.2", "10.4", "10.5","11.0", "11.1", "11.2", "11.4", "11.5"]tvOS:version: ["11.0", "11.1", "11.2", "11.3", "11.4","12.0", "12.1", "12.2", "12.3", "12.4","13.0", "13.2", "13.3", "13.4","14.0", "14.2", "14.3", "14.4", "14.5", "14.6", "14.7","15.0", "15.1", "15.2", "15.3", "15.4", "15.5", "15.6","16.0", "16.1", "16.2", "16.3", "16.4", "16.5", "16.6","17.0", "17.1", "17.2", "17.3", "17.4", "17.5", "17.6","18.0", "18.1", "18.2", "18.3", "18.4", "18.5", "18.6"]sdk: ["appletvos", "appletvsimulator"]sdk_version: [null, "11.3", "11.4", "12.0", "12.1", "12.2", "12.4","13.0", "13.2", "13.3", "13.4", "14.0", "14.2", "14.3", "14.4", "14.5", "15.0","15.2", "15.4", "15.5", "16.0", "16.1", "16.4", "17.0", "17.1", "17.2", "17.4", "17.5","18.0", "18.1", "18.2", "18.4", "18.5"]visionOS:version: ["1.0", "1.1", "1.2", "1.3", "2.0", "2.1", "2.2", "2.3", "2.4", "2.5", "2.6"]sdk: ["xros", "xrsimulator"]sdk_version: [null, "1.0", "1.1", "1.2", "1.3", "2.0", "2.1", "2.2", "2.4", "2.5"]Macos:version: [null, "10.6", "10.7", "10.8", "10.9", "10.10", "10.11", "10.12", "10.13", "10.14", "10.15","11.0", "11.1", "11.2", "11.3", "11.4", "11.5", "11.6", "11.7","12.0", "12.1", "12.2", "12.3", "12.4", "12.5", "12.6", "12.7","13.0", "13.1", "13.2", "13.3", "13.4", "13.5", "13.6", "13.7","14.0", "14.1", "14.2", "14.3", "14.4", "14.5", "14.6", "14.7","15.0", "15.1", "15.2", "15.3", "15.4", "15.5", "15.6"]sdk_version: [null, "10.13", "10.14", "10.15", "11.0", "11.1", "11.2", "11.3", "12.0", "12.1","12.3", "12.4", "13.0", "13.1", "13.3", "14.0", "14.2", "14.4", "14.5","15.0", "15.1", "15.2", "15.4", "15.5"]subsystem:null:catalyst:ios_version: *ios_versionAndroid:api_level: [ANY]ndk_version: [null, ANY]FreeBSD:SunOS:AIX:Arduino:board: [ANY]Emscripten:Neutrino:version: ["6.4", "6.5", "6.6", "7.0", "7.1"]baremetal:VxWorks:version: ["7"]
arch: [x86, x86_64, ppc32be, ppc32, ppc64le, ppc64,armv4, armv4i, armv5el, armv5hf, armv6, armv7, armv7hf, armv7s, armv7k, armv8, armv8_32, armv8.3, arm64ec,sparc, sparcv9,mips, mips64, avr, s390, s390x, asm.js, wasm, wasm64, sh4le,e2k-v2, e2k-v3, e2k-v4, e2k-v5, e2k-v6, e2k-v7,riscv64, riscv32,xtensalx6, xtensalx106, xtensalx7,tc131, tc16, tc161, tc162, tc18]
compiler:sun-cc:version: ["5.10", "5.11", "5.12", "5.13", "5.14", "5.15"]threads: [null, posix]libcxx: [libCstd, libstdcxx, libstlport, libstdc++]gcc:version: ["4.1", "4.4", "4.5", "4.6", "4.7", "4.8", "4.9","5", "5.1", "5.2", "5.3", "5.4", "5.5","6", "6.1", "6.2", "6.3", "6.4", "6.5","7", "7.1", "7.2", "7.3", "7.4", "7.5","8", "8.1", "8.2", "8.3", "8.4", "8.5","9", "9.1", "9.2", "9.3", "9.4", "9.5","10", "10.1", "10.2", "10.3", "10.4", "10.5","11", "11.1", "11.2", "11.3", "11.4", "11.5","12", "12.1", "12.2", "12.3", "12.4", "12.5","13", "13.1", "13.2", "13.3", "13.4","14", "14.1", "14.2", "14.3","15", "15.1", "15.2"]libcxx: [libstdc++, libstdc++11]threads: [null, posix, win32, mcf]  # Windows MinGWexception: [null, dwarf2, sjlj, seh]  # Windows MinGWcppstd: [null, 98, gnu98, 11, gnu11, 14, gnu14, 17, gnu17, 20, gnu20, 23, gnu23, 26, gnu26]cstd: [null, 99, gnu99, 11, gnu11, 17, gnu17, 23, gnu23]msvc:version: [170, 180, 190, 191, 192, 193, 194]update: [null, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9]runtime: [static, dynamic]runtime_type: [Debug, Release]cppstd: [null, 14, 17, 20, 23]toolset: [null, v110_xp, v120_xp, v140_xp, v141_xp]cstd: [null, 11, 17]clang:version: ["3.3", "3.4", "3.5", "3.6", "3.7", "3.8", "3.9", "4.0","5.0", "6.0", "7.0", "7.1","8", "9", "10", "11", "12", "13", "14", "15", "16", "17","18", "19", "20", "21"]libcxx: [null, libstdc++, libstdc++11, libc++, c++_shared, c++_static]cppstd: [null, 98, gnu98, 11, gnu11, 14, gnu14, 17, gnu17, 20, gnu20, 23, gnu23, 26, gnu26]runtime: [null, static, dynamic]runtime_type: [null, Debug, Release]runtime_version: [null, v140, v141, v142, v143, v144]cstd: [null, 99, gnu99, 11, gnu11, 17, gnu17, 23, gnu23]apple-clang:version: ["5.0", "5.1", "6.0", "6.1", "7.0", "7.3", "8.0", "8.1", "9.0", "9.1","10.0", "11.0", "12.0", "13", "13.0", "13.1", "14", "14.0", "15", "15.0","16", "16.0", "17", "17.0"]libcxx: [libstdc++, libc++]cppstd: [null, 98, gnu98, 11, gnu11, 14, gnu14, 17, gnu17, 20, gnu20, 23, gnu23, 26, gnu26]cstd: [null, 99, gnu99, 11, gnu11, 17, gnu17, 23, gnu23]intel-cc:version: ["2021.1", "2021.2", "2021.3", "2021.4", "2022.1", "2022.2","2022.3", "2023.0", "2023.1", "2023.2", "2024.0", "2024.1","2025.0", "2025.1"]update: [null, ANY]mode: ["icx", "classic", "dpcpp"]libcxx: [null, libstdc++, libstdc++11, libc++]cppstd: [null, 98, gnu98, "03", gnu03, 11, gnu11, 14, gnu14, 17, gnu17, 20, gnu20, 23, gnu23]runtime: [null, static, dynamic]runtime_type: [null, Debug, Release]qcc:version: ["4.4", "5.4", "8.3"]libcxx: [cxx, gpp, cpp, cpp-ne, accp, acpp-ne, ecpp, ecpp-ne]cppstd: [null, 98, gnu98, 11, gnu11, 14, gnu14, 17, gnu17]mcst-lcc:version: ["1.19", "1.20", "1.21", "1.22", "1.23", "1.24", "1.25"]libcxx: [libstdc++, libstdc++11]cppstd: [null, 98, gnu98, 11, gnu11, 14, gnu14, 17, gnu17, 20, gnu20, 23, gnu23]emcc:# From https://github.com/emscripten-core/emscripten/blob/main/ChangeLog.md# There is no ABI compatibility guarantee between versionsversion: [ANY]libcxx: [null, libstdc++, libstdc++11, libc++]threads: [null, posix, wasm_workers]cppstd: [null, 98, gnu98, 11, gnu11, 14, gnu14, 17, gnu17, 20, gnu20, 23, gnu23, 26, gnu26]cstd: [null, 99, gnu99, 11, gnu11, 17, gnu17, 23, gnu23]build_type: [null, Debug, Release, RelWithDebInfo, MinSizeRel]

通過settings.yml文件,設置的可能值都在同一個文件中定義。這樣做是為了確保名稱和拼寫的一致性,并在用戶和開源軟件社區之間建立一個統一的設置模型。
對于設置的一些特殊信息:

  • 如果某個設置允許設置為任意值,那么就可以使用“ANY”這個選項。
  • 如果某個設置允許設置為任意值,或者也可以不進行設置,那么您可以使用 [null, ANY] 這種組合。
    這個配置文件可以根據任何需求進行修改,包括添加新的設置或子設置及其值。如果希望使用工程中的settings.yml文件,可以使用conan config install命令將指定的setting.yml文件安裝(覆蓋)到Conan家目錄。
4、環境變量

可用于配置 Conan 某些行為的環境變量非常少。這些環境變量屬于例外情況,對于自定義和配置控制,Conan使用global.conf配置以及profile文件的[conf]部分。

環境變量說明
CONAN_HOME控制Conan的家目錄,默認沒有定義,使用~/.conan2
CONAN_DEFAULT_PROFILE指定一個不同于“default”的默認profile名
5、二進制模型

二進制模型是Conan包管理的核心。它通過對profile配置(setting + options + dependencies versions)進行哈希運算獲取package_id,確定了包的唯一性。
而profile中,各配置項保證了C/C++ API接口的兼容性,ABI接口的兼容性,從而實現對二進制文件的管理和分發。
另外Conan二進制模型具有可擴展性,用戶可以定義自定義設置、選項和配置,以塑造其自身二進制文件的特性。

在這里插入圖片描述
在這里插入圖片描述

三、一個完整的工程demo

1、創建cmake工程
(1)創建工程
  • C++源文件
// source/main.cpp
#include <iostream>
#include <cstdint>std::int32_t main(void)
{std::cout << "Hello World!" << std::endl;return 0;
}
  • C++測試文件
// test/main.cpp
#include <gtest/gtest.h>TEST(ExampleTest, StringTest) {std::string str = "Hello";EXPECT_EQ(str, "Hello");EXPECT_NE(str, "World");
}int main(int argc, char **argv) {::testing::InitGoogleTest(&argc, argv);return RUN_ALL_TESTS();
}
  • cmake文件
# CMakeLists.txt
cmake_minimum_required(VERSION 3.28)project(ConanDemo VERSION 1.0.0 LANGUAGES CXX)set(CMAKE_CXX_STANDARD 14)
set(CMAKE_CXX_STANDARD_REQUIRED ON)add_executable(${PROJECT_NAME})
target_sources(${PROJECT_NAME}PRIVATEsource/main.cpp
)set_target_properties(${PROJECT_NAME}PROPERTIESRUNTIME_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/bin
)find_package(GTest)add_executable(${PROJECT_NAME}_test)
target_sources(${PROJECT_NAME}_testPRIVATEtest/main.cpp
)target_link_libraries(${PROJECT_NAME}_testPRIVATEGTest::gtest_main
)set_target_properties(${PROJECT_NAME}_testPROPERTIESRUNTIME_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/bin
)enable_testing()
add_test(NAME ${PROJECT_NAME}_testCOMMAND ${PROJECT_NAME}_test
)
  • 當前工程結構
$ tree
.
|-- CMakeLists.txt
|-- source
|   `-- main.cpp
`-- test`-- main.cpp
(2)基于cmake構建驗證
# 配置cmake
cmake -S . -B build
# 構建目標
cmake --build build
# 運行test
cmake --build build --target test
2、添加conan管理
(1)設計conan配置文件
  • setting.yml文件
os:Linux:platform: [null, host, pi4]
arch: [x86_64, armv7, armv7hf, armv8, armv8_32, riscv64, riscv32]
compiler:gcc:version: ["4.1", "4.4", "4.5", "4.6", "4.7", "4.8", "4.9","5", "5.1", "5.2", "5.3", "5.4", "5.5","6", "6.1", "6.2", "6.3", "6.4", "6.5","7", "7.1", "7.2", "7.3", "7.4", "7.5","8", "8.1", "8.2", "8.3", "8.4", "8.5","9", "9.1", "9.2", "9.3", "9.4", "9.5","10", "10.1", "10.2", "10.3", "10.4", "10.5","11", "11.1", "11.2", "11.3", "11.4", "11.5","12", "12.1", "12.2", "12.3", "12.4", "12.5","13", "13.1", "13.2", "13.3", "13.4","14", "14.1", "14.2", "14.3","15", "15.1", "15.2"]libcxx: [libstdc++, libstdc++11]threads: [null, posix, win32, mcf]  # Windows MinGWexception: [null, dwarf2, sjlj, seh]  # Windows MinGWcppstd: [null, 98, gnu98, 11, gnu11, 14, gnu14, 17, gnu17, 20, gnu20, 23, gnu23, 26, gnu26]cstd: [null, 99, gnu99, 11, gnu11, 17, gnu17, 23, gnu23]clang:version: ["3.3", "3.4", "3.5", "3.6", "3.7", "3.8", "3.9", "4.0","5.0", "6.0", "7.0", "7.1","8", "9", "10", "11", "12", "13", "14", "15", "16", "17","18", "19", "20", "21"]libcxx: [null, libstdc++, libstdc++11, libc++, c++_shared, c++_static]cppstd: [null, 98, gnu98, 11, gnu11, 14, gnu14, 17, gnu17, 20, gnu20, 23, gnu23, 26, gnu26]runtime: [null, static, dynamic]runtime_type: [null, Debug, Release]runtime_version: [null, v140, v141, v142, v143, v144]cstd: [null, 99, gnu99, 11, gnu11, 17, gnu17, 23, gnu23]build_type: [null, Debug, Release, RelWithDebInfo]
  • profile文件
# host_x86_64
[settings]
arch=x86_64
build_type=Release
compiler=gcc
compiler.cppstd=gnu17
compiler.libcxx=libstdc++11
compiler.version=13
os=Linux
os.platform=host
# pi4_aarch64
[settings]
arch=armv8
build_type=Release
compiler=gcc
compiler.cppstd=gnu17
compiler.libcxx=libstdc++11
compiler.version=13
os=Linux
os.platform=pi4
(2)添加conanfile.py文件
# conanfile.py
from conan import ConanFile
from conan.tools.cmake import CMakeToolchain, CMake, cmake_layout, CMakeDepsclass ConanDemo(ConanFile):name = "hello"version = "1.0"# Optional metadatalicense = "<Put the package license here>"author = "<Put your name here> <And your email here>"url = "<Package recipe repository url here, for issues about the package>"description = "<Description of hello package here>"topics = ("<Put some tag here>", "<here>", "<and here>")# Binary configurationsettings = "os", "compiler", "build_type", "arch"options = {"shared": [True, False], "fPIC": [True, False]}default_options = {"shared": False, "fPIC": True}# Sources are located in the same place as this recipe, copy them to the recipeexports_sources = "CMakeLists.txt", "source/*", "test/*"def config_options(self):passdef layout(self):cmake_layout(self)def generate(self):deps = CMakeDeps(self)deps.generate()tc = CMakeToolchain(self)tc.generate()def build(self):cmake = CMake(self)cmake.configure()cmake.build()def package(self):cmake = CMake(self)cmake.install()def package_info(self):self.cpp_info.libs = ["hello"]
(3)安裝配置文件
  • 當前的工程結構
$ tree
.
|-- CMakeLists.txt
|-- conan
|   |-- profiles
|   |   |-- host_x86_64
|   |   `-- pi4_aarch64
|   `-- settings.yml
|-- conanfile.py
|-- source
|   `-- main.cpp
`-- test`-- main.cpp
  • 安裝Conan配置
# 創建默認的profile
conan profile detect
# 安裝指定的conan配置
conan config install conan

注:conan config install conan會將conan文件下的所有文件復制到Conan的家目錄。

  • 檢查安裝的profile
$ conan profile list
Profiles found in the cache:
default
host_x86_64
pi4_aarch64
(4)基于conan創建包
  • 執行命令
# 清除已有構建
conan remove hello# 使用默認的profile創建包
conan create . 
# 使用host_x86_64創建包
conan create . -pr=host_x86_64
# 使用pi4_aarch64創建包
conan create . -pr=pi4_aarch64
  • 檢查conan包
$ tree ~/.conan2/p -L 2
/root/.conan2/p
|-- b
|   |-- hello97f3ea6988f96
|   |-- hello9cf30133a2f6d
|   `-- hellob394c1d27f95b
|-- cache.sqlite3
|-- hello066c562205912
|   |-- d
|   |-- e
|   |-- es
|   `-- s
`-- t

conan cache中還是包含挺多文件:工程的源碼文件、conan的生成文件、構建后的輸出文件等,可以在自己本地搭建環境運行后自行查看。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/pingmian/95524.shtml
繁體地址,請注明出處:http://hk.pswp.cn/pingmian/95524.shtml
英文地址,請注明出處:http://en.pswp.cn/pingmian/95524.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

核心高并發復雜接口重構方案

核心高并發復雜接口重構方案 一、重構目標與原則 核心目標 提升接口性能:降低響應時間,提高吞吐量,降低資源使用 增強可維護性:拆解復雜邏輯,模塊化設計,降低后續迭代成本 保障穩定性:通過架構優化和灰度策略,確保重構過程無服務中斷 提升擴展性:設計靈活的擴展點,…

C++容器內存布局與性能優化指南

C容器的內存布局和緩存友好性對程序性能有決定性影響。理解這些底層機制&#xff0c;能幫你寫出更高效的代碼。 一、容器內存布局概述 不同容器在內存中的組織方式差異顯著&#xff0c;這直接影響了它們的訪問效率和適用場景。容器類型內存布局特點元數據位置元素存儲位置std::…

Beautiful.ai:AI輔助PPT工具高效搞定排版,告別熬夜做匯報煩惱

你是不是每次做 PPT 都頭大&#xff1f;找模板、調排版、湊內容&#xff0c;熬大半夜出來的東西還沒眼看&#xff1f;尤其是遇到 “明天就要交匯報” 的緊急情況&#xff0c;打開 PPT 軟件半天&#xff0c;光標在空白頁上晃來晃去&#xff0c;連標題都想不出來 —— 這種抓瞎的…

阿里云攜手MiniMax構建云原生數倉最佳實踐:大模型時代的 Data + AI 數據處理平臺

MiniMax簡介MiniMax是全球領先的通用人工智能科技公司。自2022年初成立以來&#xff0c;MiniMax以“與所有人共創智能”為使命&#xff0c;致力于推動人工智能科技前沿發展&#xff0c;實現通用人工智能(AGI&#xff09;。MiniMax自主研發了一系列多模態通用大模型&#xff0c;…

一鍵生成PPT的AI工具排名:2025年能讀懂你思路的AI演示工具

人工智能正在重塑PPT制作方式&#xff0c;讓專業演示變得觸手可及。隨著人工智能技術的飛速發展&#xff0c;AI生成PPT工具已成為職場人士、學生和創作者提升效率的得力助手。這些工具通過智能算法&#xff0c;能夠快速將文本、數據或創意轉化為結構化、視覺化的演示文稿&#…

數據庫基礎知識——聚合函數、分組查詢

目錄 一、聚合函數 1.1 count 1.1.1 統計整張表中所有記錄的總條數 1.1.2 統計單列的數據 1.1.3 統計單列記錄限制條件 1.2 sum 1.3 avg 1.4 max, min 二、group by 分組查詢 2.1 語法 2.2 示例 2.3 having 一、聚合函數 常用的聚合函數 函數說明count ([distinc…

改 TDengine 數據庫的時間寫入限制

一 sql連數據庫改 改 TDengine 數據庫的時間寫入限制 之前默認了可寫入時間為一個月&#xff0c;調整為10年&#xff0c;方便測試&#xff1a; SHOW DATABASES;use wi; SELECT CONCAT(ALTER TABLE , table_name, KEEP 3650;) FROM information_schema.ins_tables WHERE db_…

數碼視訊TR100-OTT-G1_國科GK6323_安卓9_廣東聯通原機修改-TTL燒錄包-可救磚

數碼視訊TR100-OTT-G1_國科GK6323_安卓9_廣東聯通原機修改-TTL燒錄包-可救磚刷機教程數碼視訊 TR100-G1 TTL 燒錄刷機教程固件由廣東聯通 TR100-G1 28 原版修改&#xff0c;測試一切正常1、把刷機文件解壓出 備用&#xff0c;盒子主板接好 TTL&#xff0c;不會接自行查找 TTl 接…

TVS防護靜電二極管選型需要注意哪些參數?-ASIM阿賽姆

TVS防護靜電二極管選型關鍵參數詳解TVS(Transient Voltage Suppressor)二極管作為電路防護的核心器件&#xff0c;在電子設備靜電防護(ESD)、浪涌保護等領域發揮著重要作用。本文將系統性地介紹TVS二極管選型過程中需要重點關注的參數指標&#xff0c;幫助工程師做出合理選擇。…

項目經理為什么要有一張PMP?認證?

在項目管理日益成為企業核心競爭力的今天&#xff0c;PMP已成為項目經理職業發展的重要“通行證”。這張由美國項目管理協會&#xff08;PMI&#xff09;頒發的全球公認證書&#xff0c;不僅是專業能力的象征&#xff0c;更在職業競爭力、項目成功率、團隊協作等多個維度為項目…

Qt中QSettings的鍵值使用QDataStream進行存儲

1. QDataStream介紹 數據流是編碼信息的二進制流&#xff0c;與主機的操作系統、CPU 或字節順序完全無關。例如&#xff0c;Windows 系統下 PC 寫入的數據流可由運行 Solaris 的 Sun SPARC 讀取。 您還可以使用數據流讀/寫raw unencoded binary data 。如果需要 "解析 &…

Typer 命令行工具使用示例

Typer 命令行工具使用示例 示例1&#xff1a;簡單問候程序 代碼 import typerapp typer.Typer()app.command() def greet(name: str):"""簡單的問候命令"""typer.echo(f"Hello {name}!")if __name__ "__main__":app()使用…

關于CAN總線bus off 理論標準 vs 工程實踐

我是穿拖鞋的漢子,魔都中堅持長期主義的汽車電子工程師。 老規矩,分享一段喜歡的文字,避免自己成為高知識低文化的工程師: 做到欲望極簡,了解自己的真實欲望,不受外在潮流的影響,不盲從,不跟風。把自己的精力全部用在自己。一是去掉多余,凡事找規律,基礎是誠信;二是…

CAN堆棧

PDU映射到HOH將硬件對象句柄HOH抽象成為硬件抽象層CanIf將pdu映射到硬件對象句柄上一個HOH代表一個Can控制器的一個消息緩沖區發送緩存區當所有Can硬件資源被占用時&#xff0c;LPDU存儲在緩沖區中。發送取消為了解決優先級反轉的問題&#xff0c;高優先級L-PDU會請求取消低優先…

sub3G和sub6G的區別和聯系

Sub-3G 和 Sub-6G 的區別與聯系Sub-3G 和 Sub-6G 是無線通信中頻段的不同分類&#xff0c;尤其在4G LTE和5G網絡中&#xff0c;定義了無線信號傳輸的不同頻率范圍。具體來說&#xff0c;Sub-3G 通常指的是低于3 GHz的頻段&#xff0c;而 Sub-6G 是指低于6 GHz的頻段。這些頻段的…

【數據可視化-106】華為2025上半年財報分析:用Python和Pyecharts打造炫酷可視化大屏

&#x1f9d1; 博主簡介&#xff1a;曾任某智慧城市類企業算法總監&#xff0c;目前在美國市場的物流公司從事高級算法工程師一職&#xff0c;深耕人工智能領域&#xff0c;精通python數據挖掘、可視化、機器學習等&#xff0c;發表過AI相關的專利并多次在AI類比賽中獲獎。CSDN…

Scikit-learn Python機器學習 - 特征預處理 - 歸一化 (Normalization):MinMaxScaler

鋒哥原創的Scikit-learn Python機器學習視頻教程&#xff1a; 2026版 Scikit-learn Python機器學習 視頻教程(無廢話版) 玩命更新中~_嗶哩嗶哩_bilibili 課程介紹 本課程主要講解基于Scikit-learn的Python機器學習知識&#xff0c;包括機器學習概述&#xff0c;特征工程(數據…

LINUX_Ubunto學習《2》_shell指令學習、gitee

0、前言&#xff1a; 0.1、為什么學習shell腳本 學習Shell&#xff08;Shell腳本編程&#xff09;是提升系統管理和開發效率的重要技能&#xff0c;尤其在Linux/Unix環境中作用顯著。Shell是用戶與操作系統內核的接口&#xff0c;學習Shell有助于掌握系統工作原理。shell的核心…

系統安裝與遷移工具,一鍵下載系統并制作U盤啟動盤

大家好&#xff0c;今天想跟大家分享一款非常實用的軟件——Hasleo WinToUSB 下載地址獲取 點擊獲取&#xff1a;WinToUSB啟動盤 打開后的界面&#xff1b; image Windows To Go USB 可以安裝或克隆 Windows 到 USB 設備&#xff0c;作為便攜式 Windows 使用 可以選擇直接用…

日語學習-日語知識點小記-構建基礎-JLPT-N3階段(26):文法+單詞第8回3 復習 +考え方6

日語學習-日語知識點小記-構建基礎-JLPT-N3階段&#xff08;&#xff12;6&#xff09;&#xff1a;文法單詞第8回3 復習1、前言&#xff08;1&#xff09;情況說明&#xff08;2&#xff09;工程師的信仰2、知識點1ー V辭書形 &#xff0b; ことができます。2ーこの橋、&am…