将float转换为int:复杂情况下的舍入(ceil()和floor()不可用)

时间:2010-10-20 09:58:41

标签: c++ floating-point rounding

我想将浮点值转换为其整数表示。由于这将用于比较,默认的舍入模式(round_to_nearest)不适合我。据我所知,我不能以符合C ++标准的方式指定FPU的舍入模式(甚至不是在C ++ 0x中)。有哪些方法可以实现这一目标,哪一种方法最便携?我在Linux,GCC,i386 + x86-64上编程。

谢谢!

修改

我对round_toward_infinity和round_toward_neg_infinity舍入模式感兴趣,我希望每次都能选择其中一种。

7 个答案:

答案 0 :(得分:2)

您应该使用floorceil。原型是 int floor或int ceil,但它们确实返回一个整数值。

#include <math.h>
#include <stdio.h>

int main()
{
        float x = 6.04;
        printf("floor = %f ceil = %f\n", floor(x), ceil(x));
        return 0;
}

产地:

$ ./test 
floor = 6.000000 ceil = 7.000000

所以你现在必须得出答案。

答案 1 :(得分:2)

如果12.314.7都是浮点数,那么在IEEE 754中,13.014.0都是浮点数(更一般地说:给定两个非整数浮点数,所有整数都在之间也是漂浮物)。因此,在IEEE 754下,floorceil始终正常工作(请注意x86使用IEEE 754表示)。

如果您不符合IEEE 754,请注意floor的定义(C99:7.12.9.2 / 3,我没有C90方便)

  

floor函数返回不大于x的最大整数值,表示为浮点数。

如果无法准确表示不大于x的最大整数值,我不知道如何解释。

答案 2 :(得分:2)

由于C99有llrint(),它使用当前的舍入模式(可以由fesetround()设置)舍入到下一个(long long)整数。

答案 3 :(得分:1)

您必须指定想要的舍入类型。

用这些术语来思考:

  1. 采用浮点变量

  2. 适当地围绕它

  3. 强制转换为整数将得到浮点值的整数部分 - 截断

  4. 您可以分别查看floor()ceil()进行向下舍入和向上舍入。

    你必须特别注意你想要在0和负数附近发生的事情。

    GLIBC有lots of rounding functions可用。

    这是一个圆向无穷大的功能:

    int round_towards_infinity(double value) {
      if(value > 0)
         return ceil(value);
      return floor(value);
    }
    

答案 4 :(得分:0)

也许是这样的:

#include <cmath>

int Round( const double a )
{
  return static_cast< int >( std::floor( a + 0.5 ) );
}

答案 5 :(得分:0)

我一直被教导使用的转换(虽然我确信适当的浮点数学家会为我拍摄)但是:

float x = ....;
int   y = int(x + 0.5f);

通过我的参考快速浏览说,C99有一个“lrint”系列函数,它们采用浮点值并返回长整数。这可能就是你要找的东西。

答案 6 :(得分:0)

听起来你不得不做一些纠结才能得到正确的答案。提取浮点数的指数并使用它来将尾数的位模式移位正确的数量。你可能需要做一些额外的技巧来处理+/-无穷大和溢出以及非规范化的值......但这听起来像是一条痛苦的道路......如果你真的不需要,我就不会走它。