今天看到这样一段项目代码,某个函数传入了一个void类型的指针,并在函数内部将其强转为了某结构体类型指针,利用该指针获取结构体中变量之后,又将指针转换为char类型并偏移结构体大小的长度获取数据。代码如下
void recv_omu_data(const void *data, void **ret_date....)
{
pub_head_t *head = (pub_head_t *)data; // 将指针转换为了pub_head_t传给head
int msg_len = head->msg_len;
int num = *(int *)((char *)data + sizeof(pub_head_t));
char *list = (char *)data + sizeof(omu_msg_t);
....
}
其中的结构体变量类型如下
typedef struct {
int msg_type;
int msg_len;
} pub_head_t;
// 附上另一结构体实现
typedef struct {
pub_head_t msg_head;
int num;
} omu_msg_t;
该函数里面先是将传入的指针强转为了pub_head_t类型,之后又偏移了该结构体大小的位置,继续读取值,看到这里我产生了一丝疑问,传入的指针指向某块内存,该块内存数据被强制转换为了pub_head_t结构体类型,那么该内存块的大小应该就是该指针类型的大小,为什么后面又偏移了sizeof(pub_head_t)去读取数据?难道指针类型强转并没有将传入指针所指向内存数据全部转换,只是转换了指针首地址某部分数据?
带着这个疑问写了一段测试代码验证了一下自己的猜想,结果正如自己猜想那样,如下:
运行结果
由此可见C语言指针类型强转的本质是,原指针指向的内存数据类型会被转换为所转换指针的类型,其范围是该指针类型的大小,而不是原指针指向的整块内存。