在頭文件中定義float ? ? ? nextafterf( float from, float to );(1)(since C99)
double ? ? ?nextafter( double from, double to );(2)(since C99)
long double nextafterl( long double from, long double to );(3)(since C99)
float ? ? ? nexttowardf( float from, long double to );(4)(since C99)
double ? ? ?nexttoward( double from, long double to );(5)(since C99)
long double nexttowardl( long double from, long double to );(6)(since C99)
Defined in header
#define nextafter(from, to)(7)(since C99)
#define nexttoward(from, to)(8)(since C99)
1-3)首先,將兩個參數都轉換為函數的類型,然后返回下一個可表示值from的方向to。如果from等于to,to則返回。
4-6)首先,將第一個參數轉換為函數的類型,然后返回下一個可表示值from的方向to。如果from等于to,to則返回,轉換long double為函數的返回類型,但不會丟失范圍或精度。
7)類型 - 通用宏:如果任何參數具有類型long double,nextafterl則被調用。否則,如果任何參數具有整數類型或具有類型double,nextafter則被調用。否則,nextafterf被調用。
8)類型 - 通用宏:如果參數from具有類型long double,nexttowardl則被調用。否則,如果from有整數類型或類型double,nexttoward則調用。否則,nexttowardf被調用。
參數
from, to-浮點值
返回值
如果沒有錯誤發生,下一個可表示值from的方向to。返回。如果from等于to,則to返回,轉換為函數的類型。
如果范圍誤差由于發生溢出,±HUGE_VAL,±HUGE_VALF,或±HUGE_VALL被返回(與相同的符號from)。
如果由于下溢而發生范圍錯誤,則返回正確的結果。
錯誤處理
按照math_errhandling中的指定報告錯誤。
如果實現支持IEEE浮點運算(IEC 60559),
如果from是有限的,但預期的結果是無窮大,提高FE_INEXACT和FE_OVERFLOW
如果from不相等to,結果是低于正常或零,則引發FE_INEXACT和FE_UNDERFLOW
在任何情況下,返回值都與當前舍入模式無關
如果是from或者to是NaN,則返回NaN
筆記
POSIX指定溢出和下溢條件是范圍錯誤(可能會設置錯誤)。
IEC 60559建議from每當返回from==to。這些函數會返回to,這會使零之間的行為保持一致:nextafter(-0.0, +0.0)返回+0.0并nextafter(+0.0, -0.0)返回–0.0。
例
#include?#include?#include?#include?
int?main(void){
float?from1?=?0,?to1?=?nextafterf(from1,?1);????printf("The?next?representable?float?after?%.2f?is?%.20g?(%a)\n",?from1,?to1,?to1);
float?from2?=?1,?to2?=?nextafterf(from2,?2);????printf("The?next?representable?float?after?%.2f?is?%.20f?(%a)\n",?from2,?to2,?to2);
double?from3?=?nextafter(0.1,?0),?to3?=?0.1;????printf("The?number?0.1?lies?between?two?valid?doubles:\n"???????????"????%.56f?(%a)\nand?%.55f??(%a)\n",?from3,?from3,?to3,?to3);
//?difference?between?nextafter?and?nexttoward:
long?double?dir?=?nextafterl(from1,?1);?//?first?subnormal?long?double
float?x?=?nextafterf(from1,?dir);?//?first?converts?dir?to?float,?giving?0????printf("Using?nextafter,?next?float?after?%.2f?(%a)?is?%.20g?(%a)\n",
from1,?from1,?x,?x);
x?=?nexttowardf(from1,?dir);????printf("Using?nexttoward,?next?float?after?%.2f?(%a)?is?%.20g?(%a)\n",
from1,?from1,?x,?x);
//?special?values????{
#pragma?STDC?FENV_ACCESS?ON????????feclearexcept(FE_ALL_EXCEPT);
double?from4?=?DBL_MAX,?to4?=?nextafter(from4,?INFINITY);????????printf("The?next?representable?double?after?%.2g?(%a)?is?%.23f?(%a)\n",
from4,?from4,?to4,?to4);????????if(fetestexcept(FE_OVERFLOW))?puts("???raised?FE_OVERFLOW");????????if(fetestexcept(FE_INEXACT))?puts("???raised?FE_INEXACT");????}?//?end?FENV_ACCESS?block
float?from5?=?0.0,?to5?=?nextafter(from5,?-0.0);????printf("nextafter(+0.0,?-0.0)?gives?%.2g?(%a)\n",?to5,?to5);}
輸出:
The?next?representable?float?after?0.00?is?1.4012984643248170709e-45?(0x1p-149)The?next?representable?float?after?1.00?is?1.00000011920928955078?(0x1.000002p+0)The?number?0.1?lies?between?two?valid?doubles:????0.09999999999999999167332731531132594682276248931884765625?(0x1.9999999999999p-4)and?0.1000000000000000055511151231257827021181583404541015625??(0x1.999999999999ap-4)Using?nextafter,?next?float?after?0.00?(0x0p+0)?is?0?(0x0p+0)Using?nexttoward,?next?float?after?0.00?(0x0p+0)?is?1.4012984643248170709e-45?(0x1p-149)The?next?representable?double?after?1.8e+308?(0x1.fffffffffffffp+1023)?is?inf?(inf)
raised?FE_OVERFLOW
raised?FE_INEXACTnextafter(+0.0,?-0.0)?gives?-0?(-0x0p+0)
參考
C11標準(ISO / IEC 9899:2011):7.12.11.3 nextafter函數(p:256)
7.12.11.4 nexttoward函數(p:257)
7.25類型通用數學(p:373-375)
F.10.8.3 nextafter函數(p:529)
F.10.8.4 nexttoward函數(p:529)
C99標準(ISO / IEC 9899:1999):7.12.11.3 nextafter函數(p:237)
7.12.11.4 nexttoward函數(p:238)
7.22類型通用數學(p:335-337)
F.9.8.3 nextafter函數(p:466)
F.9.8.4 nexttoward函數(p:466)