news 2026/7/15 2:42:53

target_include_directories对比 PUBLIC / PRIVATE

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
target_include_directories对比 PUBLIC / PRIVATE

提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档

文章目录

  • 一、表述详解
      • 核心结论
      • 补充核心定义(关键)
  • 二、完整项目示例
    • 1. 项目目录结构
    • 2. 源码文件
      • `include/lib.h`(库的公共接口)
      • `src/lib.cpp`(库的实现文件)
      • `src/main.cpp`(主程序)
    • 3. CMake 构建脚本
      • 写法1:使用 `PUBLIC`(标准正确用法)
      • 写法2:错误演示(改用 `PRIVATE`)
    • 4. 编译与效果测试
      • 编译命令(终端执行)
      • 结果对比
  • 三、`PRIVATE` 的**正确使用场景**
    • 调整后的目录结构
    • 新增文件:`src/private_inc/internal.h`
    • 修改 `src/lib.cpp`
    • 优化后的 CMake 配置
      • 效果
  • 四、总结

通过实操对比PUBLIC/PRIVATE的效果

一、表述详解

cmake_demo/ ├── include/ │ └── lib.h# 带导出宏的头文件├── src/ │ ├── lib.cpp# 动态库实现│ └── main.cpp# 调用方程序└── CMakeLists.txt

核心结论

target_include_directories(mylib PRIVATE 路径)的适用场景:
该头文件路径仅被lib.cpp(库的实现文件)使用,不会被main.cpp(依赖该库的外部代码)包含,此时用PRIVATE
如果外部代码(main.cpp)需要包含这个路径下的头文件(lib.h),必须用PUBLIC,否则外部目标会找不到头文件。


补充核心定义(关键)

作用域适用场景
PUBLIC路径既给lib.cpp用,也给所有依赖 mylib 的目标(如main.cpp)用(接口头文件路径)
PRIVATE路径仅给lib.cpp自用,不传递给外部依赖目标(库内部私有头文件路径)
INTERFACE路径不给自身用,仅传递给外部依赖目标

二、完整项目示例

1. 项目目录结构

采用标准工程规范,公共头文件放在include目录,源文件放在src目录:

cmake_demo/ ├── include/ # 公共头文件目录(外部可访问) │ └── lib.h # 库接口声明 ├── src/ │ ├── lib.cpp # 库实现文件 │ └── main.cpp # 主程序(调用库函数) └── CMakeLists.txt # 构建脚本

2. 源码文件

include/lib.h(库的公共接口)

头文件保护宏防止重复包含,声明加法函数,会被main.cpp直接包含:

#ifndefLIB_H#defineLIB_H// 加法函数声明:对外提供的接口intadd(inta,intb);#endif// LIB_H

src/lib.cpp(库的实现文件)

包含公共头文件,实现加法逻辑:

// 包含库的接口头文件#include"lib.h"// 实现加法函数intadd(inta,intb){returna+b;}

src/main.cpp(主程序)

调用库的add函数,需要包含lib.h

#include<stdio.h>// 包含库的公共头文件#include"lib.h"intmain(){intres=add(10,20);printf("10 + 20 = %d\n",res);return0;}

3. CMake 构建脚本

写法1:使用PUBLIC(标准正确用法)

因为main.cpp需要依赖include路径找到lib.h,因此路径需要传递给外部目标,用PUBLIC

cmake_minimum_required(VERSION 3.15) project(AddLibraryDemo) # C++标准配置 set(CMAKE_CXX_STANDARD 11) set(CMAKE_CXX_STANDARD_REQUIRED ON) # 1. 创建静态库目标 mylib add_library(mylib src/lib.cpp) # 2. 为库添加头文件路径:PUBLIC 表示路径自身可用,且传递给依赖它的目标 target_include_directories(mylib PUBLIC include) # 3. 创建可执行目标 add_executable(main_app src/main.cpp) # 4. 链接库:main_app 会自动继承 mylib 的 PUBLIC/INTERFACE 头文件路径 target_link_libraries(main_app PRIVATE mylib)

写法2:错误演示(改用PRIVATE

如果我们把PUBLIC改为PRIVATE,代表include路径仅给 mylib 自身使用,不传递

# 仅修改这一行,其余代码不变 target_include_directories(mylib PRIVATE include)

4. 编译与效果测试

编译命令(终端执行)

# 创建构建目录并进入mkdirbuild&&cdbuild# 生成构建文件cmake..# 编译make

结果对比

  1. PUBLIC配置:编译成功,运行./main_app,输出:
    10 + 20 = 30
  2. PRIVATE配置编译直接报错,提示找不到头文件:
    fatal error: lib.h: No such file or directory #include "lib.h"
    原因:main_app无法继承include路径,编译器找不到头文件。

三、PRIVATE正确使用场景

为了让你理解PRIVATE不是无用的,我们扩展场景:给库添加私有内部头文件,仅lib.cpp使用,外部无需访问。

调整后的目录结构

cmake_demo/ ├── include/ # 公共头文件(对外) │ └── lib.h ├── src/ │ ├── private_inc/ # 库私有头文件(仅内部用) │ │ └── internal.h │ ├── lib.cpp │ └── main.cpp └── CMakeLists.txt

新增文件:src/private_inc/internal.h

#ifndefINTERNAL_H#defineINTERNAL_H// 库内部使用的工具函数,不对外部暴露staticintcalc(intx){returnx*2;}#endif

修改src/lib.cpp

#include"lib.h"// 包含私有内部头文件#include"internal.h"intadd(inta,intb){// 调用内部工具函数returncalc(a+b);}

优化后的 CMake 配置

公共路径用PUBLIC,私有路径用PRIVATE

cmake_minimum_required(VERSION 3.15) project(AddLibraryDemo) set(CMAKE_CXX_STANDARD 11) set(CMAKE_CXX_STANDARD_REQUIRED ON) add_library(mylib src/lib.cpp) # 公共头文件:传递给外部依赖目标 target_include_directories(mylib PUBLIC include) # 私有头文件:仅库自身使用,不传递 target_include_directories(mylib PRIVATE src/private_inc) add_executable(main_app src/main.cpp) target_link_libraries(main_app PRIVATE mylib)

效果

  1. main_app能继承include路径,正常找到lib.h
  2. main_app无法访问src/private_inc路径,保证了库内部实现的封装性;
  3. lib.cpp可以同时找到公共头文件和私有头文件。

四、总结

  1. 表述纠正main.cpp依赖该头文件路径时,必须用PUBLIC;仅lib.cpp依赖时,才用PRIVATE
  2. 核心规则
    • 对外暴露的接口头文件路径 →PUBLIC(传递给依赖目标);
    • 库内部私有的实现头文件路径 →PRIVATE(仅自身使用,封装隔离);
  3. 单目标/多目标通用:这套规则是现代CMake的标准规范,无论项目大小都推荐使用,比全局的include_directories更安全、更易维护。
版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/7/1 20:15:00

毕设题目-贾明(网上答疑辅导系统

目录网上答疑辅导系统概述系统核心功能技术实现方案系统特色与创新点应用前景与扩展方向项目技术支持可定制开发之功能亮点源码获取详细视频演示 &#xff1a;文章底部获取博主联系方式&#xff01;同行可合作网上答疑辅导系统概述 网上答疑辅导系统是一种基于互联网的教育辅助…

作者头像 李华
网站建设 2026/7/1 20:15:35

Linux:分包上传文件

目录分包合并解压分包 推荐使用360压缩 合并 cat xxx.zip.* > xxx.zip解压 unzip xxx.zip

作者头像 李华
网站建设 2026/7/1 20:14:58

C 环境设置

C 环境设置 引言 C语言作为一种历史悠久且应用广泛的编程语言,在系统编程、嵌入式开发等领域有着举足轻重的地位。在进行C语言编程之前,必须正确设置C语言开发环境。本文将详细介绍C语言环境的设置,包括开发工具的选择、编译器的安装、环境变量的配置等内容。 开发工具选…

作者头像 李华
网站建设 2026/7/13 14:25:18

AI上下文工程解密:提示工程架构师的终极指南

AI上下文工程解密&#xff1a;提示工程架构师的终极指南 一、引言&#xff1a;为什么你的AI总是“听不懂”&#xff1f; 1.1 一个扎心的痛点&#xff1a;你写的Prompt&#xff0c;AI真的懂吗&#xff1f; 上周凌晨3点&#xff0c;我在客户的AI客服系统排查问题——用户明明说…

作者头像 李华
网站建设 2026/7/14 21:35:13

提示工程学习型组织知识管理工具:架构师的10个推荐

提示工程学习型组织知识管理工具&#xff1a;架构师的10个推荐 关键词 提示工程&#xff08;Prompt Engineering&#xff09;、学习型组织&#xff08;Learning Organization&#xff09;、知识管理&#xff08;Knowledge Management&#xff09;、工具选型&#xff08;Tool Se…

作者头像 李华
网站建设 2026/7/15 0:24:16

Cassandra 性能优化:10 个技巧让你的查询速度翻倍

Cassandra 性能优化&#xff1a;10 个技巧让你的查询速度翻倍 关键词&#xff1a;Cassandra 性能优化、数据模型设计、分区键优化、复制策略、二级索引、SSTable 压缩、一致性级别、连接池配置、硬件调优、监控工具 摘要&#xff1a;本文系统解析 Apache Cassandra 性能优化的核…

作者头像 李华