Код, безусловно, должен передавать float
, а не unsigned
.
// int floatExp(unsigned f)
int floatExp(float f)
Используйте isfinite
и frexpf()
.
#include <math.h>
int floatExp2(float value) {
int exp;
if (isfinite(value)) {
frexpf(&exp);
return exp;
}
return tmax;
}
Для основания 10 немного больше работы.
#include <math.h>
int floatExp10_(float value) {
if (isfinite(value)) {
if (value == 0.0) return 0;
float exp = log10f(fabsf(value));
// use floorf() rather than `(int) exp`.
// This does the proper rounding when `exp` is + or -
return (int) floorf(exp);
}
return tmax;
}
C не определяет, что числа с плавающей запятой и float
имеют "восемь битов экспоненты". Он также не определяет, что показатель степени является двоичным. Во многих реализациях используется двоичный формат с плавающей запятой одинарной точности IEEE 754: binary32, который имеет 8-битная экспонента со смещением степени 2.
Хак-способ - использовать союз. Этот непереносимый метод сильно зависит от знания формата с плавающей запятой, размера целого числа, порядка байтов числа с плавающей запятой и целого числа. Следующее или его вариант может работать в среде OP.
int floatExp_hack(float value) {
if (isfinite(value)) {
union {
float f;
value unsigned long ul;
} u;
assert(sizeof u.f == sizeof u.ul);
u.f = value;
return (u.ul >> 23) & 0xFF;
}
return tmax;
}
person
chux - Reinstate Monica
schedule
03.03.2014
frexp
? (frexpf
для поплавка) - person torek   schedule 03.03.2014