当前位置:  开发笔记 > 编程语言 > 正文

Epsilon四倍精度(gcc)

如何解决《Epsilon四倍精度(gcc)》经验,为你挑选了1个好方法。

根据维基百科,不同精度数据类型的布局为

单精度:指数(e):8位,分数(f):23位

双精度:e:11位,f:52位

四倍精度:e:15位,f:112位。

我写了一个小程序来输出C ++中的floatdoublelong double的数值限制(与g ++编译)

#include
#include
#include

template
void print(std::string name) {
    std::cout << name << " (" << sizeof(T) * 8 << "): " << std::numeric_limits::epsilon() << "\t"  <<  std::numeric_limits::min() << "\t" <<  std::numeric_limits::max() << std::endl;
}

int main() {
    std::cout.precision(5);
    print("float");
    print("double");
    print("long double");
    return 0;
}

哪个输出(我已经在多台机器上运行了相同的结果)

float (32): 1.1921e-07  1.1755e-38  3.4028e+38
double (64): 2.2204e-16 2.2251e-308 1.7977e+308
long double (128): 1.0842e-19   3.3621e-4932    1.1897e+4932

上限与2 ^(2 ^(e-1))一致,对于floatdouble,ε与2 ^(-f)一致。对于较长的double,按照该逻辑,ε应当约为1.9259e-34。

有谁知道,为什么没有呢?



1> Evg..:

long double不保证将其实现为IEEE-745的四倍精度。C ++参考内容为:

long double-扩展的精度浮点类型。不一定映射到IEEE-754要求的类型。通常在x86和x86-64体系结构上使用80位x87浮点类型。

如果long double实现为80位x86扩展精度,则epsilon为。这是您作为输出获得的值。2-63 = 1.0842e-19

一些编译器支持 __float128具有四倍精度的类型。在GCC long double成为一个别名__float128,如果-mlong-double-128命令行选项被使用,并且在x86_64目标__float128被保证是IEEE四倍精度类型(在软件中实现)。

std::numeric_limits并非专为__float128。要获得epsilon的值,可以使用以下技巧(假设使用低端字节序的机器):

__float128 f1 = 1, f2 = 1;      // 1.q       -> ...00000000
std::uint8_t u = 1;
std::memcpy(&f2, &u, 1);        // 1.q + eps -> ...00000001
std::cout << double(f2 - f1);   // Output: 1.9259e-34

使用GCC,您可以使用libquadmath:

#include 
...

std::cout << (double)FLT128_EPSILON;

获得相同的输出。

推荐阅读
雨天是最美
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有