Logb
定义于头文件 <cmath>
中。
描述
从浮点参数num
中提取无偏的与基无关的指数值,并将其作为浮点值返回。
库为所有 cv-unqualified 浮点类型提供了 std::logb 的重载,作为参数 num
的类型 (C++23 起)。
为所有整数类型提供了额外的重载,它们被视为double。
形式上,对于非零的num
,无偏指数是 logr|num| 的带符号整数部分(此函数将其作为浮点值返回),其中r
是std::numeric_limits<T>::radix
,T
是num
的浮点类型。如果num
是次正规数,则将其视为已规范化。
声明
- C++23
- C++11
// 1)
constexpr /* floating-point-type */
logb ( /* floating-point-type */ num );
// 2)
constexpr float logbf( float num );
// 3)
constexpr long double logbl( long double num );
// 4)
template< class Integer >
constexpr double logb ( Integer num );
// 1)
float logb ( float num );
// 2)
double logb ( double num );
// 3)
long double logb ( long double num );
// 4)
float logbf( float num );
// 5)
long double logbl( long double num );
// 6)
template< class Integer >
double logb ( Integer num );
参数
num
- 浮点或整数值
返回值
如果没有发生错误,则num
的无偏指数将作为带符号浮点值返回。
如果发生域错误,则返回实现定义的值。
如果发生极点错误,则返回-HUGE_VAL
、-HUGE_VALF
或-HUGE_VALL
。
错误处理
错误按 math_errhandling 中指定的方式报告。
如果num
为零,则可能发生域错误或范围错误。
如果实现支持 IEEE 浮点运算(IEC 60559)
如果num
是±0
,则返回-∞
并引发FE_DIVBYZERO。如果num
是±∞
,则返回+∞
。如果num
是NaN,则返回NaN。在所有其他情况下,结果是精确的(FE_INEXACT从不引发),并且当前舍入模式被忽略。
备注
POSIX要求如果num
是±0
,则发生极点错误。
std::logb
返回的指数值总是比std::frexp
返回的指数值小1,因为归一化要求不同:对于std::logb
返回的指数e
,|num*r-e|
在1和r
之间(通常在1和2之间),但对于std::fre
xp返回的指数e
,|num*2-e|
在0.5和1之间。
额外的重载不需要完全按照额外重载提供。它们只需要足以确保对于其整数类型的参数 num
,
std::logb(num)
与std::logb(static_cast<double>(num))
具有相同的效果。
示例
#include <cfenv>
#include <cmath>
#include <iostream>
#include <limits>
// #pragma STDC FENV_ACCESS ON
int main()
{
double f = 123.45;
std::cout
<< "Given the number " << f << " or "
<< std::hexfloat << f << std::defaultfloat
<< " in hex,\n";
double f3;
double f2 = std::modf(f, &f3);
std::cout
<< "modf() makes "
<< f3 << " + " << f2
<< '\n';
int i;
f2 = std::frexp(f, &i);
std::cout
<< "frexp() makes "
<< f2 << " * 2^" << i
<< '\n';
i = std::ilogb(f);
std::cout
<< "logb()/ilogb() make "
<< f / std::scalbn(1.0, i) << " * "
<< std::numeric_limits<double>::radix
<< "^" << std::ilogb(f) << '\n';
// error handling
std::feclearexcept(FE_ALL_EXCEPT);
std::cout
<< "logb(0) = "
<< std::logb(0) << '\n';
if (std::fetestexcept(FE_DIVBYZERO))
std::cout
<< "FE_DIVBYZERO raised\n";
}
Given the number 123.45 or 0x1.edccccccccccdp+6 in hex,
modf() makes 123 + 0.45
frexp() makes 0.964453 * 2^7
logb()/ilogb() make 1.92891 * 2^6
logb(0) = -Inf
FE_DIVBYZERO raised