跳到主要内容

MATH_ERRNO, MATH_ERREXCEPT, math_errhandling

描述

宏常量 math_errhandling 扩展为一个 int 类型的表达式,该表达式等于 MATH_ERRNO,或等于 MATH_ERREXCEPT,或等于它们的位或 (MATH_ERRNO | MATH_ERREXCEPT)。

math_errhandling 的值表示浮点运算符和函数执行的错误处理类型

常量解释 MATH_ERREXCEPT 表示使用浮点异常:在 <cfenv> 中至少定义了 FE_DIVBYZEROFE_INVALIDFE_OVERFLOWMATH_ERRNO 表示浮点操作使用变量 errno 报告错误。

如果实现支持 IEEE 浮点算术 (IEC 60559),则 math_errhandling & MATH_ERREXCEPT 必须是非零。

识别以下浮点错误条件

条件解释errno浮点异常示例
域错误参数超出操作在数学上定义的范围(每个函数的描述列出了所需的域错误)EDOMFE_INVALIDstd::acos(2)
极点错误函数的数学结果正好是无限或未定义的ERANGEFE_DIVBYZEROstd::log(0.0), 1.0/0.0
由于溢出的范围错误数学结果是有限的,但舍入后变为无限,或向下舍入后变为可表示的最大有限值ERANGEFE_OVERFLOWstd::pow(DBL_MAX,2)
由于下溢的范围错误结果非零,但舍入后变为零,或变为次正规数并损失精度ERANGE 或不变(实现定义)FE_UNDERFLOW 或无(实现定义)DBL_TRUE_MIN/2
不精确结果结果必须舍入以适应目标类型不变FE_INEXACT 或无(未指定)std::sqrt(2), 1.0/10.0

声明

自 C++11 起
#define MATH_ERRNO        

#define MATH_ERREXCEPT

#define math_errhandling /*implementation defined*/

备注

数学库函数是否引发 FE_INEXACT 通常未指定,但可以在函数描述中明确指定(例如 std::rintstd::nearbyint

在 C++11 之前,未指定浮点异常,任何域错误都需要 EDOM,溢出需要 ERANGE,下溢则由实现定义。

示例

#include <iostream>
#include <cfenv>
#include <cmath>
#include <cerrno>
#include <cstring>
#pragma STDC FENV_ACCESS ON
int main()
{
std::cout
<< "MATH_ERRNO is "
<< (math_errhandling & MATH_ERRNO ? "set" : "not set") << '\n'
<< "MATH_ERREXCEPT is "
<< (math_errhandling & MATH_ERREXCEPT ? "set" : "not set") << '\n';
std::feclearexcept(FE_ALL_EXCEPT);
errno = 0;
std::cout
<< "log(0) = "
<< std::log(0) << '\n';
if(errno == ERANGE)
std::cout
<< "errno = ERANGE ("
<< std::strerror(errno) << ")\n";
if(std::fetestexcept(FE_DIVBYZERO))
std::cout
<< "FE_DIVBYZERO (pole error) reported\n";
}

可能结果
MATH_ERRNO is set
MATH_ERREXCEPT is set
log(0) = -inf
errno = ERANGE (Numerical result out of range)
FE_DIVBYZERO (pole error) reported

MATH_ERRNO, MATH_ERREXCEPT, math_errhandling

描述

宏常量 math_errhandling 扩展为一个 int 类型的表达式,该表达式等于 MATH_ERRNO,或等于 MATH_ERREXCEPT,或等于它们的位或 (MATH_ERRNO | MATH_ERREXCEPT)。

math_errhandling 的值表示浮点运算符和函数执行的错误处理类型

常量解释 MATH_ERREXCEPT 表示使用浮点异常:在 <cfenv> 中至少定义了 FE_DIVBYZEROFE_INVALIDFE_OVERFLOWMATH_ERRNO 表示浮点操作使用变量 errno 报告错误。

如果实现支持 IEEE 浮点算术 (IEC 60559),则 math_errhandling & MATH_ERREXCEPT 必须是非零。

识别以下浮点错误条件

条件解释errno浮点异常示例
域错误参数超出操作在数学上定义的范围(每个函数的描述列出了所需的域错误)EDOMFE_INVALIDstd::acos(2)
极点错误函数的数学结果正好是无限或未定义的ERANGEFE_DIVBYZEROstd::log(0.0), 1.0/0.0
由于溢出的范围错误数学结果是有限的,但舍入后变为无限,或向下舍入后变为可表示的最大有限值ERANGEFE_OVERFLOWstd::pow(DBL_MAX,2)
由于下溢的范围错误结果非零,但舍入后变为零,或变为次正规数并损失精度ERANGE 或不变(实现定义)FE_UNDERFLOW 或无(实现定义)DBL_TRUE_MIN/2
不精确结果结果必须舍入以适应目标类型不变FE_INEXACT 或无(未指定)std::sqrt(2), 1.0/10.0

声明

自 C++11 起
#define MATH_ERRNO        

#define MATH_ERREXCEPT

#define math_errhandling /*implementation defined*/

备注

数学库函数是否引发 FE_INEXACT 通常未指定,但可以在函数描述中明确指定(例如 std::rintstd::nearbyint

在 C++11 之前,未指定浮点异常,任何域错误都需要 EDOM,溢出需要 ERANGE,下溢则由实现定义。

示例

#include <iostream>
#include <cfenv>
#include <cmath>
#include <cerrno>
#include <cstring>
#pragma STDC FENV_ACCESS ON
int main()
{
std::cout
<< "MATH_ERRNO is "
<< (math_errhandling & MATH_ERRNO ? "set" : "not set") << '\n'
<< "MATH_ERREXCEPT is "
<< (math_errhandling & MATH_ERREXCEPT ? "set" : "not set") << '\n';
std::feclearexcept(FE_ALL_EXCEPT);
errno = 0;
std::cout
<< "log(0) = "
<< std::log(0) << '\n';
if(errno == ERANGE)
std::cout
<< "errno = ERANGE ("
<< std::strerror(errno) << ")\n";
if(std::fetestexcept(FE_DIVBYZERO))
std::cout
<< "FE_DIVBYZERO (pole error) reported\n";
}

可能结果
MATH_ERRNO is set
MATH_ERREXCEPT is set
log(0) = -inf
errno = ERANGE (Numerical result out of range)
FE_DIVBYZERO (pole error) reported