零长数组(柔性数组、可变数组)的使用

本文探讨了定长数组与变长数组在内存管理上的差异。通过对比,指出定长数组可能导致内存冗余,而变长数组可以更有效地利用内存。介绍了如何使用变长数组在结构体中动态分配内存,从而减少内存浪费,并简化内存释放过程。此外,还阐述了变长数组在结构体中的应用及其对内存管理的影响。
摘要由CSDN通过智能技术生成

说这个话题之前,先来谈谈定长数组。

定长数组

定长数组就是长度固定数组。比如我们收发报文的缓冲区,采用定长数组去表示:

typedef struct
{
	unsigned int meg_len;
	char msg_data[MSG_LEN];
} MsgBuffer;

这里MSG_LEN是固定大小的,比如,MSG_LEN = 1024;也就是说我们每次使用都至少要申请sizeof(int) + sizeof(char)*1024=1028个bytes,但是如果我们收发包小于1024怎么办?岂不就浪费了内存,导致数组冗余吗!

怎么解决呢?最直接的办法就是做成指针结构体,如下:

typedef struct
{
	unsigned int meg_len;
	char *msg_data;
} MsgBuffer;

这样就可以解决了,申请内存大小 = sizeof(int)+sizeof(char*)但是会带来其他问题,在使用时:

//内存申请
p_buffer = (MsgBuffer *)malloc(sizeof(MsgBuffer));
if(NULL != p_buffer){
	p_buffer->msg_len = cur_len;
	p_buffer->msg_data = (char*)malloc(sizeof(char *)*cur_len;
	if(NULL != p_buffer->msg_data){
		memcpy(p_buffer->data,data,cur_len);
	}
}
//内存释放
free(p_buffer->data);
free(p_buffer);
p_buffer = NULL;

这里产生了新的问题,就是需要两次申请内存,需要分别的管理,就需要释放两次,一不小心忘记释放,就会造成内存泄露。

变长数组

变长数组(variable-length array),也简称VLA。
变长数组既数组大小待定的数组, C语言中结构体的最后一个元素可以是大小未知的数组,也就是所谓的0长度,所以我们可以用结构体来创建变长数组。

typedef struct
{
	unsigned int meg_len; //至少包含一个成员
	char msg_data[];	  //变长数组成员必须是结构体最后一个
} MsgBuffer;

使用

//内存申请
p_buffer = (MsgBuffer *)malloc(sizeof(MsgBuffer) + sizeof(int) * cur_len);
if(NULL != p_buffer){
	p_buffer->msg_len = cur_len;
	memcpy(p_buffer->data,data,cur_len);
}
//内存释放
free(p_buffer);
p_buffer = NULL;

此时就只用管理一次。

  • 用途
    它的主要用途是为了满足需要变长度的结构体,为了解决使用数组时内存的冗余数组的越界问题。

  • 用法
    在一个结构体的最后 ,声明一个长度为空的数组,就可以使得这个结构体是可变长的。对于编译器来说,此时长度为0的数组并不占用空间,因为数组名本身不占空间,它只是一个偏移量, 数组名这个符号本身代 表了一个不可修改的地址常量 (注意:数组名永远都不会是指针! ),但对于这个数组的大小,我们可以进行动态分配,对于编译器而言,数组名仅仅是一个符号,它不会占用任何空间,它在结构体中,只是代表了一个偏移量,代表一个不可修改的地址常量!

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值