CMake实战Http+编译、链接选项的使用

@bit::Shadow
✧(≖ ◡ ≖✿

目录

文件结构

CMakeLists.txt

编译选项

[可见性级别 PRIVATE PUBLIC INTERFACE](#可见性级别 PRIVATE PUBLIC INTERFACE)

优化级别了解

优化级别详解

常用优化级别

具体区别

-O0 (无优化)

-O1 (基本优化)

[-O2 (标准优化) ⭐ 最常用](#-O2 (标准优化) ⭐ 最常用)

-O3 (激进优化)

实际效果示例

☆调试与发布的区别

对项目的影响

程序性能

☆对你的项目的建议

[1. 开发调试阶段](#1. 开发调试阶段)

[2. 测试阶段](#2. 测试阶段)

[3. 生产部署](#3. 生产部署)

注意事项

遇到的问题


文件结构

bash 复制代码
ubuntu@VM-0-11-ubuntu:~/e2026/Ubuntu_learning/Auguest/HTTP$ tree -I "build|CMakeCache.txt|CMakeFiles|Makefile|cmake_install.cmake|*.o|*.d|*.bin|*.log|*.save|serverTCP" --prune
.
├── CMakeLists.txt
├── Comn.hpp
├── Daemon.hpp
├── Http.hpp
├── Log.hpp
├── Mutex_MutexGuard.hpp
├── Protocol.hpp
├── Socket.hpp
├── TCPServer.cc
├── TCPServer.hpp
└── Thread.hpp

0 directories, 11 files

要求:使用Asan编译工具构建。

CMakeLists.txt

bash 复制代码
cmake_minimum_required(VERSION 3.18)
project(Http)

set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED ON)

add_executable(serverTCP TCPServer.cc)

# 编译选项
target_compile_options(serverTCP PRIVATE
    -g
    -fsanitzie=address
    -fsanitize=undefined
    -Wall
    -Wextra
)

# 针对特定目标的链接
target_link_libraries(
    jsoncpp
    -fsaniztize=address
    -fsanitize=undefined
)

编译选项

target_compile_options ( 形成目标 可见性级别选项 编译选项 )

可见性级别 PRIVATE PUBLIC INTERFACE

分别译作:私有 公有 接口

PRIVATE

作用:只对当前目标失效并不会传递给依赖于当前目标的其他目标。

使用对象:当前目标的内部实现细节。

cpp 复制代码
target_compile_options(serverTCP PRIVATE -Wall)
# -Wall 只对 serverTCP 生效
# 如果其他目标链接了 serverTCP,不会继承 -Wall

PUBLIC

作用:编译选项对当前目标生效并会传递给依赖它的所有目标。

使用场景:接口要求,所有使用者都需要

cpp 复制代码
target_compile_options(serverTCP PUBLIC -std=c++17)
# -std=c++17 对 serverTCP 生效
# 如果有 target client 链接了 serverTCP,client 也会使用 -std=c++17

实例

cpp 复制代码
add_library(mylib mylib.cpp) #此处是生成 mylib.a库
add_executable(app app.cpp)

# mylib 内部使用,但不影响 app
target_compile_options(mylib PRIVATE -O2) # 优化级别-O2

# app 和 mylib 都使用 C++17
target_compile_options(mylib PUBLIC -std=c++17)

# app 链接 mylib,会继承 PUBLIC 的选项
target_link_libraries(app PRIVATE mylib)

优化级别了解

-O2 是 GCC/Clang 编译器的优化级别选项 ,注意是大写字母 O(不是数字零),表示 Optimization level 2

优化级别详解

常用优化级别

级别 选项 说明 编译速度 运行速度 代码大小
无优化 -O0 默认,不优化 最快 最慢 中等
基本优化 -O1 基础优化 较快 较快 中等
标准优化 -O2 常用优化(推荐) 中等 较大
激进优化 -O3 激进优化 最快 最大
大小优化 -Os 优化代码大小 中等 中等 最小
速度优化 -Ofast 极致速度(可能不标准) 最快 最大

具体区别

-O0 (无优化)

cpp

复制代码
int add(int a, int b) {
    return a + b;
}
// 编译后:直接对应汇编,便于调试
// 每个变量都在内存中有位置
// 可以单步调试,查看变量值

-O1 (基本优化)

  • 删除死代码

  • 简单的常量折叠

  • 减少不必要的跳转

  • 适合:需要一定优化但还要调试

-O2 (标准优化) ⭐ 最常用

包含 -O1 的所有优化,外加:

  • 指令调度优化

  • 循环展开(部分)

  • 函数内联(部分)

  • 更激进的常量传播

  • 适合:生产环境,兼顾速度和编译时间

-O3 (激进优化)

包含 -O2 的所有优化,外加:

  • 更多函数内联

  • 循环完全展开

  • 向量化(SIMD)

  • 可能增加代码体积

  • 注意:有时会导致程序变大,甚至变慢

实际效果示例

cpp

复制代码
// 原始代码
int sum = 0;
for (int i = 0; i < 100; i++) {
    sum += array[i];
}

-O0 :按原样执行循环

-O2 :可能展开为多个累加,减少循环开销

-O3:可能使用 SIMD 向量化指令,一次处理多个数据

☆调试与发布的区别

cmake

复制代码
# Debug 版本 - 方便调试
add_compile_options(-g -O0)  # 不优化,保留调试信息

# Release 版本 - 性能优化
add_compile_options(-O2 -DNDEBUG)  # 标准优化,移除调试断言

# 高性能版本
add_compile_options(-O3 -march=native)  # 针对本机架构优化

对项目的影响

程序性能

text

复制代码
运行速度:-O3 > -O2 > -O1 > -O0
代码大小:-O3 > -O2 > -O1 > -O0

☆对你的项目的建议

1. 开发调试阶段

cmake

复制代码
target_compile_options(serverTCP PRIVATE
    -g          # 调试信息
    -O0         # 不优化,方便调试
    -Wall       # 警告
)

2. 测试阶段

cmake

复制代码
target_compile_options(serverTCP PRIVATE
    -g          # 保留调试信息
    -O1         # 轻度优化
    -Wall
)

3. 生产部署

cmake

复制代码
target_compile_options(serverTCP PRIVATE
    -O2         # 标准优化
    -DNDEBUG    # 移除 assert
    -Wall
)

注意事项

  1. -O2 可能改变程序行为 :如果有未定义行为(如越界访问),-O2 可能表现异常

  2. 调试困难-O2 优化后,单步调试时执行顺序可能混乱

  3. 推荐做法

    • 开发时用 -O0-O1

    • 测试时用 -O2

    • 发布时用 -O2-O3

对于你的 HTTP 服务器项目,-O2 是很好的选择,既能保证性能,又不会过度优化导致问题难以调试!

遇到的问题

CMakeList.txt写时末尾总是出现报错的红色波浪号(无论写至何处,并且自动补全功能失效)"我怀疑是网络的问题"

显示语法问题:函数缺少开头的"(" --- 末尾未有"("形成完整语句

复制得到

bash 复制代码
[{
	"resource": "/home/ubuntu/e2026/Ubuntu_learning/Auguest/HTTP/CMakeLists.txt",
	"owner": "cmake-configure-diags",
	"severity": 8,
	"message": "CMake Error at CMakeLists.txt:2:Unexpected end of file.\n\nParse error.  Function missing opening \"(\".",
	"source": "cmake",
	"startLineNumber": 2,
	"startColumn": 1,
	"endLineNumber": 2,
	"endColumn": 10000,
	"modelVersionId": 1,
	"origin": "extHost2"
}]

解决方式:

无脑编译。直接cmake .竟然直接跑通.....

感谢支持,长期连载

欢迎关注

相关推荐
十正16 分钟前
用 HTTP 条件请求把“强一致“和“低成本
网络·后端·http
Horn Still Sounds19 分钟前
Linux进程间通信:信号、消息队列、共享内存完整笔记
linux·网络·笔记
Fxkj88828 分钟前
传统企业布局新媒体:自行摸索与IP陪跑模式深度对比
人工智能·网络协议·tcp/ip·媒体
demon755200330 分钟前
IDEA-http-client-指南
http·intellij-idea
路弥行至37 分钟前
ROS2 通信避坑实录:从 topic/msg 底层原理到一次内存错位复盘
网络·经验分享·笔记·其他·内存·topic·ros2
Alan CGH38 分钟前
一次非寻常的压测优化经历
java·网络·压力测试
Yang96111 小时前
一人一机一手机:鼎讯G-4000A让光缆查找告别双人配合
网络
myy-learn1 小时前
27-进程通信
linux·服务器·网络
可乐鸡翅yeah_1 小时前
HTTPS 站点下 M3U8 混合内容问题深度排查,HLS 协议安全策略踩坑实录
数据库·网络协议·https·m3u8·m3u8在线