位字段成员的类型

Type of bit-field members

本文关键字:类型 成员 字段      更新时间:2023-10-16

理论上,我们有两个选项来选择位字段成员的类型:

  1. 基础类型的类型。
  2. 位数适合的最小类型。

那么位域成员的实际类型是什么(到目前为止,我在标准中找不到提示 - C 和 C++ 都一样(,C 和 C++ 之间有什么区别吗?

尽管意识到特定的编译器不是参考,但我试图通过C++函数重载和typeid运算符至少获得一些提示:

#include <typeinfo>
struct S
{
    unsigned int n4  :  4;
    unsigned int n12 : 12;
};
void f(unsigned char)
{
    std::cout << "uc" << std::endl;
}
void f(unsigned short)
{
    std::cout << "us" << std::endl;
}
void f(unsigned int)
{
    std::cout << "ui" << std::endl;
}
int main(int argc, char* argv[])
{
    S s; s.n4 = 0; s.n12 = 0;
    f(s.n4);
    f(s.n12);
    std::cout << typeid(s.n4).name() << std::endl;
    std::cout << typeid(s.n12).name() << std::endl;
    std::cout << typeid(unsigned char).name() << std::endl;
    std::cout << typeid(unsigned short).name() << std::endl;
    std::cout << typeid(unsigned int).name() << std::endl;
    return 0;
}

输出(linux 下的 GCC 5.4.0(完全令人惊讶,至少在我看来是矛盾的:

ui
ui
h
t
h
t
j

那么,如果根据typeid运算符,type分别是无符号字符和无符号短字符,为什么在重载解析期间选择无符号int?甚至可能是海湾合作委员会的错误?

附录:GCC 8.1(linux(仍然表现出相同的行为。

从C++标准§ 10.3.10.1 (class.bit(:

位字段属性不是类成员类型的一部分。

(在发布问题时,我一定忽略了标准中的这句话......

因此,标准明确了位字段成员的类型,它等于底层类型。

感谢戴维斯·赫林给了我适当的提示。