然而,我在大学开始的C ++讲座开始了我的第一个问题。我们的任务是通过IEEE 754标准在C ++中为浮点实现自制结构:
创建一个数据结构,允许您存储浮点数,读取其原始字节表示形式及其内部表示形式为s,e和m。使用union和bit-field-struct的组合。 编写一个程序,其中浮点数分配给结构的浮点部分,并打印原始和s / e / m表示。对raw和m。
使用十六进制输出
到目前为止我得到的是:
#include <stdio.h>
#include <math.h>
union {
struct KFloat {
//Using bit fields for our self made float. s sign, e exponent, m mantissa
//It should be unsigned because we simply use 0 and 1
unsigned int s : 1, e : 8, m : 23;
};
//One bit will be wasted for our '.'
char internal[33];
};
float calculateRealFloat(KFloat kfloat) {
if(kfloat.s == 0) {
return (1.0+kfloat.m)*pow(2.0, (kfloat.e-127.0));
} else if (kfloat.s == 1) {
return (-1.0)*((1.0+kfloat.m)*pow(2.0, (kfloat.e-127.0)));
}
//Error case when s is bigger 1
return 0.0;
}
int main(void) {
KFloat kf_pos = {0, 128, 1.5707963705062866};//This should be Pi (rounded) aka 3.1415927
KFloat kf_neg = {1, 128, 1.5707963705062866};//Pi negative
float f_pos = calculateRealFloat(kf_pos);
float f_neg = calculateRealFloat(kf_neg);
printf("The positive float is %f or ",f_pos);
printf("%e\n", f_pos);
printf("The negative float is %f or ",f_neg);
printf("%e", f_neg);
return 0;
}
这段代码的第一个错误显然是尾数绝对错误,但我不知道如何解决这个问题。
答案 0 :(得分:2)
请重读任务:
创建一个允许存储浮点数的数据结构, 读取其原始字节表示 及其内部表示为s,e和m。
这并不意味着你应该存储一个字符串
我会这样做:
union MyFloat
{
unsigned char rawByteDataRep[4];
unsigned int rawDataRep;
float floatRep;
struct{ // not checked this part just copied from you
unsigned s : 1;
unsigned e : 8;
unsigned m : 23;
} componentesRep;
}
但要小心! 除了广泛使用这种联合转换模式这一事实外, C-Standard 表明,如果您读取的另一个联合成员而不是写入的联合成员,则结果为未定义行为。
编辑: 添加了uint32 rep
void testMyfloat()
{
MyFloat mf;
mf.floatRep = 3.14;
printf("The float %f is assembled from sign %i magnitude 0x%08x and exponent %i and looks in memory like that 0x%08x.\n",
mf.floatRep,
(int)mf.componentesRep.s,
(unsigned int)mf.componentesRep.m,
(int)mf.componentesRep.e,
mf.componentesRep.rawDataRep);
}
答案 1 :(得分:1)
布鲁斯道森有一系列关于浮点表示和算术的博客文章。该系列的最新内容是here,其中包含一系列链接以前发布的详细讨论此主题的帖子。