• 24.0、 C语言——自定义数据类型_位段


    24.0、 C语言——自定义数据类型_位段

    位段:

    什么是位段 ->

    位段的声明和结构是类似的,但有两个不同:

            1. 位段的成员必须是: int 、 undigned int 、或 signed int;

            2. 位段的成员后边有一个冒号和一个数字; 
            3. 当然在我们查阅了大量的资料之后,可以发现不仅仅是int类型,只要是整型就行,比如short 、 char 等都可以;
            4. 但是建议大家在定义成员变量的时候,尽量都是一个类型的;

     实例代码 ->

    1. struct S {
    2. int a : 2;
    3. int b : 5;
    4. int c : 10;
    5. int d : 30;
    6. };
    7. int main() {
    8. struct S s = { 0 };
    9. printf("%d\n", sizeof(s));
    10. return 0;
    11. }

            1. 声明一个结构体 S ,定义了四个变量;
            2. 在 main() 函数中输出定义的一个 结构体的对象 s 的大小,输出结果是 -> 8
            3. 我们先来解释一下 ' : ' 后面的数字是什么意思 ->
            变量 a ,我们认为 变量 a 赋予的数据不会太大,所以不需要分配太多的内存空间,那么我们只给他 2 个 bit位 的空间,因此变量 a   ' : '   后面的 2 代表的就是给 变量a 2 个 bit 位的内存空间;
    【但是要注意不能分配超过该变量字节的 bit 位数,比如说 int 类型就不能分配超过 32 位的 bit 数】

    位段的内存分配:

            1. 位段的成员可以是 int unsigned 、int 、 signed int 或者是 char (属于整型家族)类型;
            2. 位段的空间上是按照需要以 4个字节(int)或者1个字节(char)的方式来开辟的;

            3. 位段涉及很多不确定因素 ,位段是不跨平台的,注重可移植的程序应该避免使用位段【因为C语言也没有给出明确的规定,每个编译器都是按照自己的规定去理解的,所以不支持跨平台】;

    我们将上述代码画出内存图,如下所示 -> 

    ​​​​​​​

     

    1. 所以该 结构体 S 所占用的空间为 8 个字节;
    2. 也能够看出在 VS编译器 中使用内存时 -> 从低位向高位依次去使用;  

    总结一下:
            
    我们的位段就是为了节省内存空间资源而出现的,如果不用位段的话,4 个 int 类型要占用 16 个字节的内存空间,但是用了位段之后只需要 8 个字节的内存空间即可【虽然这 8 个字节中浪费了一小部分的 bit 位空间,但是总体来说是节省了大部分的空间】;

    接下里再看看 char 类型的位段是如何存储的 ->

    1. struct S {
    2. char a : 3;
    3. char b : 4;
    4. char c : 5;
    5. char d : 4;
    6. };
    7. int main() {
    8. struct S s = { 0 };
    9. s.a = 10;
    10. s.b = 20;
    11. s.c = 3;
    12. s.d = 4;
    13. return 0;
    14. }

    最后去内存中验证的时候存储的内容确实就是 2 2 0 3 0 4 ;
    那么就能够证实 char 类型的位段是如下分配空间的 -> 

            1. 首先将第一次分配的 1字节 分配了 3 bit 给 a;然后由分配了 4 bit 给 b;
            2. 给 c 分配 5 bit 的时候发现第一次分配的 1 字节不够用了,所以又重新分配了 1 字节给你,然后再从这 1 字节中分配 5bit 给 c:
            3. 最后分配给 d 4bit的时候又发现第二次分配的 1 字节不够用了,同理再次重新分配 1 字节给你,然后再给 d 分配 4 bit 的内存空间;

    位段的跨平台问题:

            1. int 位段被当成有符号数还是无符号数是不确定的;

            2. 位段中最大位的数目不能确定;(16位机器最大16,32位及其最大32,写成27,在16位机器会出问题);

            3. 位段中的成员在内存中从左向右分配,还是从右向左分配标准尚未定义;

            4. 当一个结构包含两个位段,第二个位段成员比较大,无法容纳于第一个位段剩余的位时,是舍弃剩余的位还是利用,这是不确定的;

    总结:

            跟结构相比,位段可以达到同样的效果,但是可以很好的节省空间,但是有跨平台问题的存在;

  • 相关阅读:
    企业数字化转型-数字技术创新对企业市场价值的影响研究(数据复现)
    C#使用mysql-connector-net驱动连接mariadb报错
    某大厂高级测试岗位面试题...
    服务器虚拟化有什么好处
    MongoDB中ObjectId获取时间
    RabbitMQ中的核心概念和交换机类型
    论文阅读(单词记录)Investigating Attention Mechanism in 3D Point Cloud Object Detection
    射频微波芯片设计2:滤波器芯片
    80行代码轻松搞定反向传播神经网络(BPNN)
    Jmeter之配置元件
  • 原文地址:https://blog.csdn.net/m0_52433668/article/details/126904865