位域和联合体的使用

背景

在一次代码阅读中发现了c语言的位域和联合体的联合使用,看的不是很明白,故做笔记记录。

开头

遇到的代码内容如下:

typedef struct _tag_Uart_Drv_Data    
{
    unsigned char a : 2;
    unsigned char b : 2;
    unsigned char c : 2;
    unsigned char d : 2;

    unsigned char e : 2;
    unsigned char f : 2;
    unsigned char g : 2;  //4 5  2^4=16
    unsigned char h : 2;

    unsigned char i : 2;
    unsigned char j : 2;
    unsigned char k : 2;
    unsigned char l : 2;

    unsigned char m : 2;
    unsigned char n : 2;
    unsigned char o : 2;
    unsigned char p : 2;

    unsigned char q : 8;
    unsigned char r : 8;
    unsigned char s : 8;
    unsigned char t : 8;
    unsigned char u : 8;
} ;

typedef union _tag_Uart_Drv_DataBuf 
{
    struct _tag_Uart_Drv_Data    Bits;
    uint8_t _c[9];      //signa + checksum
}uart_dev;


结论

在一番的查资料后了解到,这里使用了C语言中的位域(bit-field)分表表示给每个变量赋值长度为2bit或8bit的长度的内存空间。
让我们再次看到结构体下面的联合体(union)中定义的内容,这里有一个结构体定义的变量Bits以及一个uint8_t型的数组_c,由union的定义可知,这两个成员变量指向的是内存中的同一片区域,也就是说对这两个变量的读写,实际上是指向内存的同一片区域,换句话说,当我们在对Bits中的成员变量进行改变时可以直接通过下面的数组来进行读,每8bit代表其中数组的一个变量,故我们可以在Bits中对成员变量赋值,在_c中对改变的变量进行读操作,这样可以大大地提高数据的读效率,尤其是在串口通信中的信息传输时。
注意:这里的abcd 4位代表的是数组_c[0],因为这8位刚和数组下标0的地址是相对应的。

posted @ 2023-06-16 08:54  stack0verflow  阅读(112)  评论(0编辑  收藏  举报