C语言定长数组 变长数组 柔性数组

C语言定长数组 变长数组 柔性数组

文章目录

  • C语言定长数组 变长数组 柔性数组
    • 1. 定长数组
    • 2. 变长数组
    • 3. 柔性数组
      • 3.1 结构体的大小
      • 3.2 柔性数组的使用

1. 定长数组

在C99标准之前,C语言在创建数组的时候,数组的大小只能使用常量常量表达式来,或者在初始化数组时,省略数组的大小,这就是所谓的定长数组

#include <stdio.h>
int main()
{int arr1[10];int arr2[10 + 5];int arr3[] = {1,2,3,4,5,6,7,8,9,10};return 0;
}

2. 变长数组

有定长数组这样的语法限制,让我们创建数组不够灵活,有时数组大小给大了浪费空间,有时数组大小给小了不够用,所以在C99标准之后,有个一个变⻓数组(variable-length array,简称 VLA)的概念,允许我们在创建数组的时候使用变量

int n = a + b;
int arr[n];

在上述示例中,arr 就是变长数组,因为它的长度取决于变量n的值,编译器没法事先确定,只有运行时才能知道变量n是多少

变长数组特点:

  1. 变长数组⻓度只有运⾏时才能确定,所以变⻓数组不能初始化
  2. 变⻓数组的意思是数组的⼤⼩是可以使⽤变量来指定的,在程序运⾏的时候,根据变量的⼤⼩来指定数组的元素个数,⽽不是说数组的⼤⼩是可变的。数组的⼤⼩⼀旦确定就不能再变化了。

在VS2022中是不支持变长数组的,没法测试,在gcc编译器上可以测试

#include <stdio.h>
int main()
{int n = 0;scanf("%d", &n);//根据输⼊数值确定数组的⼤⼩int arr[n];int i = 0;for (i = 0; i < n; i++){scanf("%d", &arr[i]);}for (i = 0; i < n; i++){printf("%d ", arr[i]);}return 0;
}

在这里插入图片描述

3. 柔性数组

那么有没有一种数组,在确定确定数组的大小,还可以根据需要扩大数组
在C99 中,结构体中的最后⼀个元素允许是未知⼤⼩的数组,这就叫做『柔性数组』成员。
例如:

struct S
{int i;char c;int arr[];
};

在上述示例中,arr就是变长数组

变长数组的特点:

  1. 在结构体中
  2. 最后一个成员
  3. 未知大小的数组

这样的数组就是柔性数组

3.1 结构体的大小

struct S
{int i;char c;int arr[];
};#include <stdio.h>
int main()
{printf("%zd\n", sizeof(struct S));return 0;
}

代码运行结果:>8
根据结构体对齐规则,int 4个字节,char 1个字节,总共5个字节,不为最大对齐数4的倍数,对齐至8字节

在存在柔性数组的结构体中,计算结构体的大小时,不会计算柔性数组的大小

3.2 柔性数组的使用

柔性数组是通过 malloc realloc的方式来实现数组大小的扩大的

代码一:

#include <stdio.h>
#include <string.h>
#include <stdlib.h>struct S
{int i;char c;int arr[];
};
int main()
{struct S* p = (struct S*)malloc(sizeof(struct S) + 10 * sizeof(int)); //通过结构体指针来访问结构体,开辟一个结构体大小 + 想要开辟数组大小的空间if (p == NULL)  //判断开辟是否成功{perror("malloc fail");return 1;}//使用柔性数组int i = 0;  for (i = 0; i < 10; i++) {p->arr[i] = i;}struct S* tmp = (struct S*)realloc(p, sizeof(struct S) + 15 * sizeof(int)); //调整数组大小if (tmp != NULL)  //判断是否调整成功{p = tmp;}else{perror("realoc fail");return 1;}//使用for (i = 10; i < 15; i++){p->arr[i] = i;}//打印for (i = 0; i < 15; i++){printf("%d ", p->arr[i]);}//释放free(p);p = NULL;return 0;
}

看不懂的可以去看看动态内存管理malloc calloc realloc free这篇博客

代码二:

#include <stdio.h>
#include <string.h>
#include <stdlib.h>struct S
{int i;char c;int *arr;
};
int main()
{struct S* p = (struct S*)malloc(sizeof(struct S));  //开辟一块空间给结构体if (p == NULL)  //判断开辟是否成功{perror("malloc fail");return 1;}p->arr = (int*)malloc(10 * sizeof(int));  //开辟数组if (p->arr == NULL)  //判断开辟是否成功{perror("malloc fail");return 1;}//使用int i = 0;for (i = 0; i < 10; i++){p->arr[i] = i;}int* tmp = (int*)realloc(p->arr,15 * sizeof(int)); //调整结构体大小if (tmp != NULL) //判断{p->arr = tmp;}else{perror("realoc fail");return 1;}//使用for (i = 10; i < 15; i++){p->arr[i] = i;}//打印for (i = 0; i < 15; i++){printf("%d ", p->arr[i]);}//释放free(p->arr);p->arr = NULL;free(p);p = NULL;return 0;
}

代码一代码二可以使用了柔性数组,但是代码一有两个好处:

  1. ⽅便内存释放
    代码一:
    示意图为连续内存,只是为了区分划分为了几块,红色部分为柔性数组调整大小的部分
    在这里插入图片描述
    代码二:
    示意图为连续内存,只是为了区分划分为了几块,红色部分为柔性数组调整大小的部分
    在这里插入图片描述
    代码一的空间是一次性在堆区上开辟的,而代码二是先开辟结构体的空间,再开辟柔性数组的空间的,而既然是开辟的空间,就需要使用free来释放,否则有可能导致内存泄漏,而代码一只需要一次释放,而代码二中结构体往往知道释放,但是结构体成员也需要释放容易被忽视,所以,如果我们把结构体的内存以及其成员要的内存⼀次性分配好了,并返回给⼀个结构体指针,做⼀次free就可以把所有的内存也给释放掉

2.这样有利于访问速度
代码一中是一块连续的内存,连续的内存有益于提⾼访问速度,也有益于减少内存碎⽚。(只是相较于代码二速度会快一点,其实,我个⼈觉得也没多⾼了,反正你跑不了要⽤做偏移量的加法来寻址)

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/226027.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【EI会议征稿】第三届电子信息工程、大数据与计算机技术国际学术会议(EIBDCT 2024)

第三届电子信息工程、大数据与计算机技术国际学术会议&#xff08;EIBDCT 2024&#xff09; 2024 3rd International Conference on Electronic Information Engineering, Big Data and Computer Technology 第三届电子信息工程、大数据与计算机技术国际学术会议&#xff08;…

小狐狸GPT付费2.4.9弹窗版学习源码介绍

小狐狸GPT付费2.4.9弹窗版学习源码是一套基于GPT&#xff08;Generative Pre-trained Transformer&#xff09;模型的开源代码库&#xff0c;旨在帮助开发者快速构建和训练自己的语言模型。该源码集成了多个先进的自然语言处理技术&#xff0c;包括预训练、微调、对话生成等&am…

云服务领取证书,注册域名,实现nginx服务配置证书

目录 1.登录网址腾讯云 2.腾讯云注册域名 3.实名认证&#xff0c;上传信息 4.域名注册 5.领取证书 6.域名与证书绑定 7.下载证书 8.设置环境 9.域名解析 10. 本地域名解析 11.上传证书到目录 12.nginx配置文件做地址重写到证书域名 13.配置证书conf 14.设置index…

磁盘坏道修复工具-是一款非常方便实用的磁盘坏道修复软件-供大家学习研究参考

1、支持磁盘数据擦除。 2、杜绝因硬盘坏道&#xff0c;而产生个人隐私数据泄露的问题。 3、支持对该磁盘格式化。 下载&#xff1a;https://download.csdn.net/download/weixin_43097956/88625682

关于“Python”的核心知识点整理大全22

目录 ​编辑 9.4.2 在一个模块中存储多个类 虽然同一个模块中的类之间应存在某种相关性&#xff0c;但可根据需要在一个模块中存储任意数量的 类。类Battery和ElectricCar都可帮助模拟汽车&#xff0c;因此下面将它们都加入模块car.py中&#xff1a; car.py my_electric_car…

基于 Gin 的 HTTP 代理上网行为记录 demo

前言: 前端时间写了好几篇使用 Gin 框架来做 HTTP 代理 demo 的文章&#xff0c;然后就想着做一个记录上网行为的小工具&#xff0c;就是简单记录看看平时访问了什么网站&#xff08;基于隧道代理的&#xff0c;不是中间人代理&#xff0c;所以只能记录去了哪里&#xff0c;不能…

wps左上角有绿色小三角的数字如何求和

1.这个状态是求和不了的&#xff0c;使用求和公式求出来的也是0 2.进行如下操作 3.转换好后 则可以求和成功了

深度学习 Day16——P5运动鞋识别

&#x1f368; 本文为&#x1f517;365天深度学习训练营 中的学习记录博客&#x1f356; 原作者&#xff1a;K同学啊 | 接辅导、项目定制 文章目录 前言1 我的环境2 代码实现与执行结果2.1 前期准备2.1.1 引入库2.1.2 设置GPU&#xff08;如果设备上支持GPU就使用GPU,否则使用C…

【Qt QML 入门】TextArea

TextArea也是一个多行文本编辑器。TextArea相比texttedit&#xff0c;增加了占位符文本&#xff0c;并添加了样式定义。 import QtQuick import QtQuick.Window import QtQuick.ControlsWindow {id: winwidth: 800height: 600visible: trueTextArea {id: taanchors.centerIn: …

解决Visual Studio 各版本都出现新建项目后解决方案下没有文件和项目问题

一步一步创建C#控制台应用程序也会出错&#xff0c;这个你可能不会相信&#xff0c;我就遇到了这么一次&#xff0c;就在刚刚&#xff0c;是的&#xff0c;我都不敢相信&#xff0c;用了这么多年的新建一个控制台程序居然不正常了。新建完毕发现里面什么都没有&#xff0c;除了…

首发卡密引流系统源码

程序特色&#xff1a; 支持个人和企业小程序广告获取卡密。 支持短视频点赞和关注获取卡密。 搭建教程&#xff1a; 环境要求&#xff1a;Nginx、MySQL 5.6、PHP 5.6 步骤&#xff1a; 将压缩包解压至网站根目录。 打开域名/install&#xff0c;按照提示填写数据库信息进行…

JS对象循环引用的危害:你知道吗?

&#x1f90d; 前端开发工程师&#xff08;主业&#xff09;、技术博主&#xff08;副业&#xff09;、已过CET6 &#x1f368; 阿珊和她的猫_CSDN个人主页 &#x1f560; 牛客高级专题作者、在牛客打造高质量专栏《前端面试必备》 &#x1f35a; 蓝桥云课签约作者、已在蓝桥云…

移动端机器学习框架 MDL 简介与实践

Mobile-deep-learning&#xff08;MDL&#xff09; MDL 是百度研发的可以部署在移动端的基于卷积神经网络实现的移动端框架&#xff0c;可以应用在图像识别领域。 具体应用&#xff1a;在手机百度 App 中&#xff0c;用户只需要点击自动拍开关&#xff0c;将手机对准物体&…

联想王传东:AI PC迈入AI Ready 即将开启AI On

“AI PC已经正式迈入AI Ready 阶段&#xff0c;接下来会逐渐进入到AI On阶段。”12月16日&#xff0c;英特尔人工智能创新应用大赛启动仪式在深圳举办。作为独家AI PC合作伙伴&#xff0c;联想集团副总裁、中国区首席市场官王传东代表公司出席仪式并致辞。 王传东认为AI PC的发…

大模型Transformer 推理 :kvCache原理浅析

大模型Transformer 推理 :kvCache原理浅析 kvCache 原理 在采样时,Transformer模型会以给定的提示/上下文作为初始输入进行推理(可以并行处理),然后逐一生成额外的标记来继续完善生成的序列(体现了模型的自回归性质)。在采样过程中,Transformer会执行自注意力操作,为…

27系列DGUS智能屏发布:可实时播放高清模拟信号摄像头视频

针对高清晰度的模拟信号摄像头视频画面的显示需求&#xff0c;迪文特推出27系列DGUS智能屏。该系列智能屏可适配常见的AHD摄像头、CVBS摄像头&#xff0c;支持单路1080P高清显示、两路720P同屏显示&#xff08;同一类型摄像头&#xff09;。用户通过DGUS简单开发即可实现摄像头…

【送书活动】智能汽车、自动驾驶、车联网的发展趋势和关键技术

文章目录 前言01 《智能汽车》推荐语 02 《SoC底层软件低功耗系统设计与实现》推荐语 03 《SoC设计指南》推荐语 05 《智能汽车网络安全权威指南&#xff08;上册&#xff09;》推荐语 06 《智能汽车网络安全权威指南&#xff08;下册&#xff09;》推荐语 后记赠书活动 前言 …

mac安装pnpm与使用

1、什么是pnpm&#xff1f; pnpm 全称 performant npm&#xff0c;意思是高性能的 npm。pnpm 由 npm/yarn 衍生而来&#xff0c;解决了 npm/yarn 内部潜在的 bug&#xff0c;极大的优化了性能&#xff0c;扩展了使用场景。被誉为 “最先进的包管理工具”。 2、pnpm特点 速度…

虚拟机启动 I/O error in “xfs_read_agi+0x95“

1.在选择系统界面按e 进入维护模式 2.找到ro把ro改成 rw init/sysroot/bin/sh 然后按Ctrlx 3.找到坏掉的分区&#xff0c;以nvme0n1p3为例进行修复 xfs_repair -d /dev/nvme0n1p3 4.init 6 重新启动 以下情况 先umount 再修复 则修复成功

接口测试 — 4.Requests库GET、Post请求

Requests库GET请求是使用HTTP协议中的GET请求方式对目标网站发起请求。 &#xff08;不带参数的GET请求请看上一篇文章的练习&#xff09; 1、Requests库待参数的GET请求 使用Get方法带参数请求时&#xff0c;是params参数字典&#xff0c;而不是data参数字典。data参数字典…