我正在考虑floor
可用的功能math.h
.它很容易使用:
#include#include int main(void) { for (double a = 12.5; a < 13.4; a += 0.1) printf("floor of %.1lf is %.1lf\n", a, floor(a)); return 0; }
如果我想编写自己的实现怎么办?看起来像这样:
#include#include double my_floor(double num) { return (int)num; } int main(void) { double a; for (a = 12.5; a < 13.4; a += 0.1) printf("floor of %.1lf is %.1lf\n", a, floor(a)); printf("\n\n"); for (a = 12.5; a < 13.4; a += 0.1) printf("floor of %.1lf is %.1lf\n", a, my_floor(a)); return 0; }
?
它似乎不适用于负数(my_floor
),但第二个看起来很好(my_floor_2
):
#include#include double my_floor(double num) { return (int)num; } double my_floor_2(double num) { if(num < 0) return (int)num - 1; else return (int)num; } int main(void) { double a1 = -12.5; printf("%lf\n", floor(a1)); printf("%lf\n", my_floor(a1)); printf("%lf\n", my_floor_2(a1)); return 0; }
程序输出:
其中一个最终是否正确?
不,你不能这样解决它.编写自己的实现的最佳方法是从平台上的C标准库中窃取一个.但请注意,可能包含特定于平台的细微差别,因此可能无法移植.
C标准库floor
函数通常很聪明,因为它不能通过转换为整数类型来工作.如果确实如此,那么您将面临signed
整数溢出的风险,其行为未定义.(请注意,a的最小可能范围int
是-32767到+32767).
精确实现还取决于平台上使用的浮点方案.
对于使用IEEE754浮点的平台和long long
类型,您可以采用此方案:
如果数字的大小大于2的53次方,则将其返回(因为它已经是整数).
否则,转换为64位类型(长很长),并将其返回.