跳转到主内容
极星编程网:以代码为星,赴技术山海!

C++怎么计算平方根 C++数学库cmath常用函数【手册】

sqrt要求非负输入,负数返回NaN且可能静默失败;需链接-libm;优先用sqrt/sqrtf而非手写;long double精度跨平台不一致。 用
sqrt
计算平方根,但必须传入非负数 直接调用
sqrt
是最常用做法,但它对负数输入不定义——在大多数平台上会返回
nan
(Not a Number),且可能触发浮点异常(取决于编译器和运行时设置)。这不是“报错”,而是静默出错,容易被忽略。 正数和零:安全,返回精确到浮点精度的平方根值 负数:返回
nan
,
std::isnan(sqrt(-1))
为 true;若开启 FPE 检查(如 GCC 的
-ftrapv
或某些调试环境),可能中断执行 类型要匹配:
sqrt(4)
调用的是
double sqrt(double)
,整数会被隐式转成
double
;想用
float
版本得写
sqrtf(4.0f)
,否则多一次类型转换
sqrtf
和
sqrtl
的实际差异不只是精度 这三个函数分别对应
float
、
double
、
long double
输入/输出。区别不止是“算得更准”,还涉及性能和 ABI 兼容性。
sqrtf
通常比
sqrt
快,尤其在向量化场景下(如启用
-march=native -ffast-math
)
sqrtl
在 x86-64 Linux 上多数实现仍是软件模拟,慢很多;Windows MSVC 下甚至可能退化为
double
精度 跨平台时别假设
long double
一定是 80-bit:Clang/LLVM 默认用 IEEE-754 binary64(即等同
double
) 编译时没链接
libm
会导致
undefined reference to sqrt
这是 Linux/macOS 上高频链接错误。C++ 标准库头文件
声明了
sqrt
,但实现体在数学库
libm
中,而 C++ 链接器默认不自动拉它。 C知道 CSDN推出的一款AI技术问答工具 下载 g++/clang++ 编译时需显式加
-lm
:例如
g++ main.cpp -lm
CMake 用户注意:
target_link_libraries(myapp m)
必须写,不能只靠
find_package(Threads)
之类掩盖 Windows MSVC 一般无此问题(数学函数内建于 libcmt),但 MinGW-w64 同样要
-lm
替代方案:手写牛顿迭代或查表法只在极端场景有用 除非你在做嵌入式裸机、GPU shader、或对某段热代码做极致优化,否则不要自己实现平方根。现代
sqrt
指令(x86 的
sqrtss
/
sqrtsd
)已高度优化,且编译器能自动向量化循环中的多次调用。 立即学习 “ C++免费学习笔记(深入) ”; 牛顿法写出来容易,但收敛性、初值选择、边界处理(比如 0、极小值)全是坑 查表法内存占用大,缓存不友好,且插值误差难控 唯一常见例外:需要整数平方根(如判断是否为完全平方数),这时用
static_cast(std::round(sqrt(n)))
再平方验证,比纯整数二分略快但可读性差 事情说清了就结束。真正容易被忽略的是:负数输入不报错、链接漏
-lm
、以及误以为
long double
在所有平台都提供扩展精度。

相关文章