C++11中的NAN

本文探讨了C++11中NAN(Not-A-Number)的特性,包括NAN不等于自身,如何使用std::isnan进行判断,以及NAN与无穷大值的区别。示例代码展示了NAN在数学运算中的行为,如std::floor对NAN的操作。同时提到了不同类型的NAN在运算时的行为差异,特别是signal_NaN在计算中可能引发异常。
摘要由CSDN通过智能技术生成

C++11中引入了NAN, NAN是Not-A-Number的简写,表示不是一个数值,那么下面的代码:

#include <cmath>
#include <iostream>
int main(int argc, const char *argv[]) {

    if (NAN == NAN) {
        std::cout << "NAN == NAN is true" << std::endl;
    } else {
        std::cout << "NAN == NAN is false" << std::endl;
    }

    float ans1 = sqrtf(-1.0f);
    if (ans1 == NAN) {
        std::cout << "ans1 == NAN is true" << std::endl;
    } else {
        std::cout << "ans1 == NAN is false" << std::endl;
    }

    if (std::isnan(ans1)) {
        std::cout << "isnan(ans) is true" << std::endl;
    } else {
        std::cout << "isnan(ans) is false" << std::endl;
    }

    if (std::isnan(NAN)) {
        std::cout << "isnan(NAN) is true" << std::endl;
    } else {
        std::cout << "isnan(NAN) is false" << std::endl;
    }

    double v = std::strtod("nan", NULL);
    if (std::isnan(v)) {
        std::cout << "isnan(v) is true: v = " << v << std::endl;
    } else {
        std::cout << "isnan(v) is false, v = " << v << std::endl;
    }

    if (std::isnan((1.0/0.0))) {
        std::cout << "isnan(1.0/0.0)) is true" << std::endl;
    } else {
        std::cout << "isnan(1.0/0.0) is false" << std::endl;
    }
    if (std::isinf((1.0/0.0))) {
        std::cout << "isinf(1.0/0.0)) is true" << std::endl;
    } else {
        std::cout << "isinf(1.0/0.0) is false" << std::endl;
    }

    if (std::isinf((1.0/-0.0))) {
        std::cout << "isinf(1.0/-0.0)) is true" << std::endl;
    } else {
        std::cout << "isinf(1.0/-0.0) is false" << std::endl;
    }

    std::cout << "floor(NAN) = " << (std::floor(NAN)) << std::endl;
    std::cout << "floor(NAN) + 1 = " << (std::floor(NAN) +1) << std::endl;

    return 0;
}

运行输出是什么呢?

NAN == NAN is false
ans1 == NAN is false
isnan(ans) is true
isnan(NAN) is true
isnan(v) is true: v = nan
isnan(1.0/0.0) is false
isinf(1.0/0.0)) is true
isinf(1.0/-0.0)) is true
floor(NAN) = nan
floor(NAN) + 1 = nan

从上面的代码中我们可以总结到:

  1. NAN和NAN之间不能用"==" 来比较,负数取平方根计算取来的结果是NAN,但是也不能用 “==” 来判断
  2. 判断是否为NAN须要用std::isnan来判断
  3. std::strtod(“nan”, NULL)返回NAN, 其它非"nan"的字符串返回0,比如std::strtod(“otherstring”, NULL)返回0
  4. 1.0/0.0不是NAN,是无穷大值,C++中用std::isinf来判断是无穷大值或者无穷小值
  5. NAN可以进行std::floor等数值运算,其结果为NAN, NAN 值进行加减等数值运算也是NAN

对于第五点,NAN又分为quiet_NaN和signal_NaN,前者在进行运算时不会抛出异常,后者会:
参考这里的示例代码:

#include <iostream>
#include <limits>
#include <cfenv>
#pragma STDC_FENV_ACCESS on
void show_fe_exceptions()
{
    int n = std::fetestexcept(FE_ALL_EXCEPT);
    if(n & FE_INVALID) std::cout << "FE_INVALID is raised\n";
    else if(n == 0)    std::cout << "no exceptions are raised\n";
    std::feclearexcept(FE_ALL_EXCEPT);
}
int main()
{
    double snan = std::numeric_limits<double>::signaling_NaN();
    std::cout << "After sNaN was obtained ";
    show_fe_exceptions();
    double qnan = snan * 2.0;
    std::cout << "After sNaN was multiplied by 2 ";
    show_fe_exceptions();
    double qnan2 = qnan * 2.0;
    std::cout << "After the quieted NaN was multiplied by 2 ";
    show_fe_exceptions();
    std::cout << "The result is " << qnan2 << '\n';
}

输出为:

After sNaN was obtained no exceptions are raised
After sNaN was multiplied by 2 FE_INVALID is raised
After the quieted NaN was multiplied by 2 no exceptions are raised
The result is nan
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值