1

我无法让以下代码正常工作。使用在线 IEEE-754 转换器,我(手动)写出 testData.txt 文件,该文件使用表示浮点数 75.5 的位字符串读取;实际的 cout.write 确实表明位字符串也符合我的预期。但是,当我尝试使用联合将 char* 强制转换为浮点数时(正如我所见,这是完成此转换的典型方法),结果浮点数不是我期望的数字。

#include<climits>
#include<iostream>
#include<fstream>
#include<bitset>

int main( int, char** )
{

    std::ifstream inputFile( "testData.txt", std::ios_base::in | std::ios_base::binary );
    if( !inputFile ) std::cout << "Failed to open input file!" << std::endl;

    char buffer[ CHAR_BIT * sizeof(float) ];
    inputFile.read( buffer, CHAR_BIT * sizeof(float) );

    std::cout << "cout.write of input from file = ";
    std::cout.write( buffer, CHAR_BIT * sizeof(float) );
    std::cout << std::endl;

    union { float f; char* c; } fToCharStarUnion;

    fToCharStarUnion.c = buffer;
    std::bitset< sizeof(float) * CHAR_BIT > bits( std::string( fToCharStarUnion.c ) );
    std::cout << "fToCharStarUnion.f = " << fToCharStarUnion.f << " bits = " << bits << std::endl;

    inputFile.close();
    return 0;
}

运行这个的返回结果是:

cout.write of input from file = 01000010100101110000000000000000
fToCharStarUnion.f = -1.61821e+38 bits = 01000010100101110000000000000000

有什么我没有做的基本事情可以使这项工作正常工作吗?

4

2 回答 2

4

您的联合需要包含一个 char 数组而不是指针。

union { float f; char c[sizeof(float)]; } float2char;

然后,您还必须担心字节顺序;是 c[0] 浮点数的指数端,或尾数的尾部。(答案会因您的硬件而异 - Intel vs PPC 或 SPARC 或......)

于 2010-02-18T19:27:20.637 回答
3

您正在使用bitset. 这会导致您的解码位位于bitset对象中,而不是union. 要从位集中获取原始位,请使用以下to_ulong方法:

#include<climits>
#include<iostream>
#include<fstream>
#include<bitset>

int main( int, char** )
{

    std::ifstream inputFile( "testData.txt",
       std::ios_base::in | std::ios_base::binary );
    if( !inputFile ) std::cout << "Failed to open input file!" << std::endl;

    char buffer[ CHAR_BIT * sizeof(float) ];
    inputFile.read( buffer, CHAR_BIT * sizeof(float) );

    std::cout << "cout.write of input from file = ";
    std::cout.write( buffer, CHAR_BIT * sizeof(float) );
    std::cout << std::endl;

    union {
        float f[ sizeof(unsigned long)/sizeof(float) ];
        unsigned long l;
    } funion;

    funion.l = std::bitset<32>( std::string( buffer ) ).to_ulong();
    std::cout << "funion.f = " << funion.f[0]
       << " bits = " << std::hex <<funion.l << std::endl;

    inputFile.close();
    return 0;
}

这通常假设您的 FPU 以与 CPU 的整数部分相同的字节序运行,并且sizeof(long) >= sizeof(float)……对double.

编辑:现在我已经使工会的成员大小相等,我看到这段代码对字节序很敏感。解码float将位于大端机器上数组的最后一个元素,小端机器上的第一个元素。:v( 。也许最好的方法是尝试给联合的整数成员与 FP 成员完全相同的位数,并在获得to_ulong.在原始代码中。

于 2010-02-18T19:44:16.927 回答