GNU libc Rounding Functions

GNU libc Rounding Functions

See also http://www.gnu.org/software/libc/manual/html_node/Rounding-Functions.html

The functions listed here perform operations such as rounding and truncation
of floating-point values. Some of these functions convert floating point
numbers to integer values. They are all declared in math.h.

You can also convert floating-point numbers to integers simply by casting
them to int. This discards the fractional part
, effectively rounding towards
zero.
However, this only works if the result can actually be represented as an
int-for very large numbers, this is impossible.
The functions listed here return the result as a double instead to get around
this problem.

The fromfp functions use the following macros, from TS 18661-1:2014, to
specify the direction of rounding.
These correspond to the rounding directions defined in IEEE 754-2008.

trunc

The trunc functions round x towards zero to the nearest integer
(returned in floating-point format). Thus,
trunc (1.5) is 1.0 and trunc (-1.5) is -1.0 (丢掉小数部分, x 大于等于 0 的时候结果
等于 floor(x), x 小于等于 0 的时候结果等于 ceil(x)
).

ceil

These functions round x upwards to the nearest integer, returning that value
as a double. Thus, ceil (1.5) is 2.0 (ceil: 天花板 — 向上(大)取整).

floor

These functions round x downwards to the nearest integer, returning that value
as a double. Thus, floor (1.5) is 1.0 and floor (-1.5) is -2.0 (
floor: 地板 — 向下(小)取整).

round

These functions are similar to rint, but they round halfway cases(一半的情况)
away from zero instead of to the nearest integer
(or other current rounding mode).
I.e. round to nearest integer, away from zero (返回 四舍五入整数).

rint

These functions round x to an integer value according to the current rounding
mode, usually 1, example 2.23-0ubuntu11 libc, gcc 5.4.0: FLT_ROUNDS is 1:

/usr/lib/gcc/x86_64-linux-gnu/5/include/float.h:128:

/* Addition rounds to 0: zero, 1: nearest, 2: +inf, 3: -inf, -1: unknown.  */
/* ??? This is supposed to change with calls to fesetround in <fenv.h>.  */
#undef FLT_ROUNDS
#define FLT_ROUNDS 1

And:

BUGS
       C99 specifies that the value of FLT_ROUNDS should reflect changes
       to the current rounding mode, as set by fesetround().  Currently,
       this does not occur: FLT_ROUNDS always has the value 1.

See also http://www.gnu.org/software/libc/manual/html_node/Floating-Point-Parameters.html#Floating-Point-Parameters

Round to nearest integer (Like round, but maybe NOT good, better use round
when nearest integer, especially “四舍五入”
, rint 返回 最接近参数的整数,
如果有两个数同样接近, 则会返回偶数的那个 !!
).

Bad rint examples

EXPECT_DOUBLE_EQ(-2.0, ::rint(-1.5));
EXPECT_DOUBLE_EQ(-2.0, ::rint(-2.5));// Here we want -3.0!
EXPECT_DOUBLE_EQ(0.0, ::rint(0.5));// Here we want 1.0!
EXPECT_DOUBLE_EQ(0.0, ::rint(-0.5));// Here we want -1.0!

Good round examples

EXPECT_DOUBLE_EQ(-2.0, ::round(-1.5));
EXPECT_DOUBLE_EQ(-3.0, ::round(-2.5));// Here we want -3.0!
EXPECT_DOUBLE_EQ(1.0, ::round(0.5));// Here we want 1.0!
EXPECT_DOUBLE_EQ(-1.0, ::round(-0.5));// Here we want -1.0!

对比

value round rint floor ceil trunc
0.1 0.0 0.0 0.0 1.0 0.0
0.5 1.0 0.0 0.0 1.0 0.0
0.6 1.0 1.0 0.0 1.0 0.0
1.1 1.0 1.0 1.0 2.0 1.0
1.5 2.0 2.0 1.0 2.0 1.0
2.3 2.0 2.0 2.0 3.0 2.0
2.5 3.0 2.0 2.0 3.0 2.0
3.8 4.0 4.0 3.0 4.0 3.0
5.5 6.0 6.0 5.0 6.0 5.0
-0.5 -1.0 -0.0 -1.0 -0.0 -0.0
-1.1 -1.0 -1.0 -2.0 -1.0 -1.0
-1.5 -2.0 -2.0 -2.0 -1.0 -1.0
-2.3 -2.0 -2.0 -3.0 -2.0 -2.0
-2.5 -3.0 -2.0 -3.0 -2.0 -2.0
-3.8 -4.0 -4.0 -4.0 -3.0 -3.0
-5.5 -6.0 -6.0 -6.0 -5.0 -5.0

See also