4

我有一个unsigned char*. 通常这指向一块数据,但在某些情况下,指针是数据,即。将int值转换为unsigned char*指针 ( unsigned char* intData = (unsigned char*)myInteger;),反之亦然。

但是,我需要使用一个float值来执行此操作,并且它不断给我转换错误。

unsigned char* data;
float myFloat = (float)data;

我怎样才能做到这一点?

4

4 回答 4

4

bit_cast:

template <class Dest, class Source>
inline Dest bit_cast(Source const &source) {
    static_assert(sizeof(Dest)==sizeof(Source), "size of destination and source objects must be equal");
    static_assert(std::is_trivially_copyable<Dest>::value, "destination type must be trivially copyable.");
    static_assert(std::is_trivially_copyable<Source>::value, "source type must be trivially copyable");

    Dest dest;
    std::memcpy(&dest, &source, sizeof(dest));
    return dest;
}

用法:

char *c = nullptr;
float f = bit_cast<float>(c);
c = bit_cast<char *>(f);
于 2012-09-13T01:10:11.240 回答
3

使用给定变量存储其他数据的唯一正确方法是按字节复制数据:

template <typename T>
void store(unsigned char * & p, T const & val)
{
    static_assert(sizeof(unsigned char *) >= sizeof(T));

    char const * q = reinterpret_cast<char const *>(&val);
    std::copy(q, q + sizeof(T), reinterpret_cast<char *>(&p));
}

用法:

unsigned char * p;
store(p, 1.5);
store(p, 12UL);

匹配检索功能:

template <typename T>
T load(unsigned char * const & p)
{
    static_assert(sizeof(unsigned char *) >= sizeof(T));

    T val;
    char const * q = reinterpret_cast<char const *>(&p);
    std::copy(q, q + sizeof(T), reinterpret_cast<char *>(&val));

    return val;
}

用法:

auto f = load<float>(p);
于 2012-09-12T23:37:46.353 回答
2

如果您的编译器支持它(GCC 支持),则使用联合。根据 C++ 标准,这是未定义的行为。

union {
    unsigned char* p;
    float f;
} pun;

pun.p = data;
float myFloat = pun.f;

如果sizeof(unsigned char *) == sizeof(float). 如果指针大于浮点数,那么您必须重新考虑您的策略。

请参阅关于类型双关语的维基百科文章,特别是关于使用 union的部分。

只要您直接使用联合而不是类型转换为联合,GCC 就允许使用联合进行类型双关......请参阅 IBM 关于类型双关问题的讨论,了解使用 GCC 进行类型双关的正确和不正确方法。

另请参阅维基百科关于强类型和弱类型的文章以及一篇关于类型双关和严格别名的深入研究的文章。

于 2012-09-13T01:35:45.097 回答
-1
unsigned char* data;
float myFloat = *(float*)data;
于 2012-09-12T23:32:16.983 回答