C语言学习笔记:动态数组

C语言学习笔记:动态数组动态数组数组是 C 语言中的很重要的一种构造类型 最初我们学习的都是静态数组 但是 静态数组有着自己难以改变的缺点 数组长度固定 一般在静态数组定义后 系统就会为其分配对应长度的连续的专有内存空间 可是 我们都知道 不同的运行样例 所需要的数组长度是不一样的 为了所有样例都可以执行 一般我们会将数组长度设置为一个很大的值 比如 我一般都是借助宏定义直接声明 1000 这个长度是可以满足我日常所需的 虽然这种方式 满足了一般运行的要求 但是它极大的浪费了内存 于是我们引出了动态数组的概念 顾名思义 动态

动态数组

数组是C语言中的很重要的一种构造类型,最初我们学习的都是静态数组,但是,静态数组有着自己难以改变的缺点——数组长度固定。

一般在静态数组定义后,系统就会为其分配对应长度的连续的专有内存空间,可是,我们都知道,不同的运行样例,所需要的数组长度是不一样的,为了所有样例都可以执行,一般我们会将数组长度设置为一个很大的值,比如:我一般都是借助宏定义直接声明1000,这个长度是可以满足我日常所需的。虽然这种方式,满足了一般运行的要求,但是它极大的浪费了内存。

于是我们引出了动态数组的概念,顾名思义,“动态”体现在数组长度可以由用户自己定义上。那么今天来总结一下,动态数组的两种实现方式。

方式1:C99变长数组

C99标准规定,我们可以通过变长数组的方式来实现动态数组,在我们程序中使用一个变量(非const值)从键盘上获取数组的长度。

//变长数组实现动态数组  #include<stdio.h> int main() { 
    int n; printf("请输入数组的长度:"); scanf("%d",&n); int sz[n]; printf("请输入数组的元素:\n"); for(int i=0; i<n; i++) scanf("%d",&sz[i]); printf("打印数组的元素:\n"); for(int i=0; i<n; i++) printf("%d\t",sz[i]); return 0; } 

在这里插入图片描述

方式2:内存管理函数

C语言提供了一系列的内存管理函数来帮助我们来按需要动态的分配和回收内存空间。这恰恰就是动态数组另一种实现方式的基础,我们可以利用内存管理中的内存申请和释放函数,在程序的运行过程中进行数组长度的指定。

那么我们先来看一下动态数组中会涉及到的常用的内存管理函数。(涉及到的头文件是:

)

(1)malloc()

  • 函数原型:
(类型说明符*) malloc(unsigned int size); 
  • 功能:在内存的动态存储区中分配一块长度size字节的连续区域。

(2)calloc()

  • 函数原型:
(类型说明符*) calloc(n,size); 

在这里,我们需要注意一下,

  • 功能:在内存的动态存储区中分配n块长度size字节的连续区域。

(3)realloc()

  • 函数原型:
(类型说明符*) realloc(void *p,int size); 
  • 功能:重新分配堆上的void指针p(可以将void*理解为任意类型的指针变量类型)所指的空间,使其长度为size个字节,同时会复制原有内容到新分配的堆上存储空间。
    注意,size可大可小(如果新的大小大于原内存大小,则新分配部分不会被初始化;如果新的大小小于原内存大小,可能会导致数据丢失)

(4) free()

  • 函数原型:
void free(void* p); 
  • 功能:释放void * p所指的内存空间

注意:

在molloc,calloc,realloc三个函数中

①类型说明符是申请的地址将要存储的数据类型;

②函数的返回值代表申请空间是否成功,如果成功,返回申请到的空间的首地址,如果不成功,返回NULL(我们后续的操作建立在空间申请成功的基础上,所以我们需要在申请空间后,通过返回值判断空间是否申请成功);

③molloc,calloc两个函数的区别在于molloc申请的是一块size空间,而calloc可以指定申请的块数,即n块size空间。

使用代码来应用一下上面的几个函数。

//以一维数组为例,展示动态数组的建立 #include <stdio.h> #include <stdlib.h> #include <string.h> int main() { 
    int *arr=NULL,*new_arr=NULL,size,new_size; printf("请输入数组长度:"); scanf("%d",&size); // arr=(int*)malloc(sizeof(int)*size); arr=(int*)calloc(size,sizeof(int)); if(arr==NULL) { 
    printf("内存申请失败!"); exit(1); } printf("请输入数组元素:"); for(int i=0; i<size; i++) { 
    scanf("%d",&arr[i]); } printf("打印数组元素:\n"); for(int i=0; i<size; i++) printf("%d\t",arr[i]); new_arr=(int*)realloc(arr,2*size*sizeof(int)); printf("\n容量扩大为原来2倍,请输入数组元素:"); for(int i=0; i<2*size; i++) { 
    scanf("%d",&new_arr[i]); } printf("\n再次打印数组元素:\n"); for(int i=0; i<2*size; i++) printf("%d\t",new_arr[i]); free(arr); return 0; } 

在这里插入图片描述
代码给出了一维数组的建立,其实二维数字也是类似的方法:先申请空间——>判断空间是否申请成功——>使用申请成功的空间——>free掉申请的空间。不过需要注意的是,二维数组的逐层申请和释放空间的顺序。

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/215841.html原文链接:https://javaforall.net

(0)
上一篇 2026年3月18日 下午1:02
下一篇 2026年3月18日 下午1:02


相关推荐

  • 裴蜀定理 【浅讲】

    裴蜀定理 【浅讲】这里证明不会讲解 因为写这篇文章的目的是为了让大家简单理解裴蜀定理 以及可以在算法题中可以运用 主要针对于做题 裴蜀定理 又称贝祖定理 特殊性 对于方程 ax by 1 只有整数 a 和 b 互质时 方程才有整数解 裴蜀定理的证明视频裴蜀定理的证明文章扩展欧几里德算法是用来在已知 a b 求解一组 x y 使它们满足裴蜀 贝祖 等式 ax by gcd a b d 扩展欧几里得算法 exgcd877 扩展欧几里得算法 https www a

    2026年3月18日
    2
  • linux下快速安装oracle客户端

    linux下快速安装oracle客户端1 首先 Oracle 官网下载安装包 nbsp http www oracle com technetwork database features instant client index 097480 html 根据访问数据的版本下载对应客户端 每种包又分 zip rpm 两种格式包 zip 包相当于解压后免安装版 rpm 包需要安装版 2 安装解压缩到 usr local oracleunzip nbsp inst

    2026年3月18日
    2
  • 人工智能立法将加快进程;“苹果税“下调5%|合规周报

    人工智能立法将加快进程;“苹果税“下调5%|合规周报

    2026年3月16日
    2
  • CmakeList的编写和参数详解「建议收藏」

    CmakeList的编写和参数详解「建议收藏」CmakeList的编写和参数详解

    2025年5月25日
    5
  • T-SQL基础–TOP

    T-SQL基础–TOP

    2021年11月26日
    51
  • 手把手教你Charles抓包工具使用

    手把手教你Charles抓包工具使用Charles简介Charles是一个HTTP代理服务器,HTTP监视器,反转代理服务器,当浏览器连接Charles的代理访问互联网时,Charles可以监控浏览器发送和接收的所有数据。它允许一个开发者查看所有连接互联网的HTTP通信,这些包括request,response和HTTPheaders(包含cookies与caching信息)。Charles主要功能支持SSL代理。可以截取分析SSL的请求。支持流量控制。可以模拟慢速网络以及等待时间(latency)较长的请求。支持AJ

    2022年4月28日
    67

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号