C语言 内存

news2025/1/14 0:48:03

内存分配

内存分配的类型

C/C++中内存分为5个区,分别为栈区、堆区、全局/静态存储区、常量存储区、代码区

静态内存分配:编译时分配,包括全局、静态全局、静态局部三种变量。

动态内存分配:运行时分配,包括栈(局部变量),堆(c语言中用到的变量被动态的分配在内存中)。

变量的内存分配

栈区

介绍
  • 栈区由编译器自动分配释放,由操作系统自动管理,无须手动管理。
  • 栈区上的内容只在函数范围内存在,当函数运行结束,这些内容也会自动被销毁。
  • 栈区按内存地址由高到低方向生长,其最大大小由编译时确定,速度快,但自由性差,最大空间不大。
  • 栈区是先进后出原则,即先进去的被堵在屋里的最里面,后进去的在门口,释放的时候门口的先出去。
存放内容
  • 临时创建的局部变量和const定义的局部变量存放在栈区。
  • 函数调用和返回时,其入口参数和返回值存放在栈区。

堆区

介绍
  • 堆区由程序员分配内存和释放。
  • 堆区按内存地址由低到高方向生长,其大小由系统内存/虚拟内存上限决定,速度较慢,但自由性大,可用空间大。

全局/静态区

  • 通常是用于那些在编译期间就能确定存储大小的变量的存储区,但它用于的是在整个程序运行期间都可见的全局变量和静态变量。
  • 全局区有 .bss段 和 .data段组成,可读可写。
.bss段
  • 未初始化的全局变量和未初始化的静态变量存放在 .bss 段。
  • 初始化为 0 的全局变量和初始化为0的静态变量存放在 .bss 段。
  • .bss 段不占用可执行文件空间,其内容由操作系统初始化。
.data段
  • 已初始化的全局变量存放在 .data 段。
  • 已初始化的静态变量存放在 .data 段。
  • .data 段占用可执行文件空间,其内容有程序初始化。

常量区

  • 字符串、数字等常量存放在常量区。
  • const修饰的全局变量存放在常量区。
  • 程序运行期间,常量区的内容不可以被修改。

代码区

  • 程序执行代码存放在代码区,其值不能修改(若修改则会出现错误)。
  • 字符串常量和define定义的常量也有可能存放在代码区。

栈区和堆区的比较

申请方式

栈由编译器管理,堆的分配和释放由程序员管理。

申请大小

栈是向低地址生长的数据结构,是一块连续的内存,能从栈中获得的内存较小,编译期间确定大小;堆是向高地址生长的数据结构,是一个不连续的储存空间,内存获取比较灵活,也较大。

栈与堆中的储存内容

栈:在函数调用时,第一个进栈的是主函数中的最后一条指令的地址,然后是函数的各个参数,在大多 数的c编译器中,参数是由右往左入栈的,然后是函数中的局部变量(静态变量是不入栈的),当本次函数调用结束后,局部变量先出栈,然后是参数,最后栈顶指针指向最开始存的地址,也就是主函数中的下一条指令,程序由该点开始运行;

堆:一般是在堆的头部用一个字节存放堆的大小,堆中的具体内容由程序员安排。

动态内存分配

malloc 函数

头文件

stdlib.hmalloc.h

函数原型

void* malloc(int size)

功能

分配长度为 size 字节的内存块

参数

只有一个参数,并且是整型

返回值

分配成功返回指向被分配内存的指针,否则返回空指针 NULL

返回值类型 void* ,在 C 语言中,void* 可以不经转换直接赋值给任何类型的指针变量(函数指针变量除外)

calloc 函数

头文件

stdlib.hmalloc.h

函数原型

void* calloc(int n,int size)

功能

分配 n 个长度为 size 字节的连续空间

返回值

分配成功返回指向分配起始地址的指针,否则返回空指针 NULL

realloc 函数

头文件

stdlib.hmalloc.h

函数原型

void* realloc(void* mem_address,int newsize)

功能

1.为已有内存的变量重新分配新的内存空间(可大、可小) ;

2.先判断当前的指针是否有足够的连续空间,如果有,扩大 mem_address 指向的地址,并且将 mem_ address 返回;

3.如果空间不够,先按照newsize指定的大小分配空间,将原有数据从头到尾拷贝到新分配的内存区域,而后释放原来 mem_address 所指内存区域(注意:原来指针是自动释放,不需要使用 free),同时返回新分配的内存区域的首地址。即重新分配存储器块的地址。

返回值

分配成功返回 mem_address 所指的内存区域,否则返回空指针 NULL

free 函数

动态分配的内存空间由程序员手动编程释放。

C 语言中,free 和 malloc、calloc、realloc 是成对出现的,有多少个 malloc,就应该有多少个 free 。

若 malloc、calloc、realloc 的个数比 free 多,会造成内存泄漏;若 malloc、calloc、realloc 的个数比 free 少,会造成二次删除,破坏内存,导致程序崩溃。

头文件

stdlib.h

函数声明

void free(void* ptr)

功能

释放之前调用 calloc、malloc 或 realloc 所分配的内存空间

参数

指针指向一个要释放内存的内存块,该内存块之前是通过调用 malloc、calloc 或 realloc 进行分配内存的。如果传递的参数是一个空指针,则不会执行任何动作。

返回值

不返回任何值

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

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

相关文章

21天学会C++:Day15----STL简介

CSDN的uu们,大家好。这里是C入门的第十五讲。 座右铭:前路坎坷,披荆斩棘,扶摇直上。 博客主页: 姬如祎 收录专栏:C专题 目录 1. 什么是STL 2. STL的版本 3.STL的六大组件 4. STL的重要性 5. 如何学…

二叉树实现表达式求值(C++)

用二叉树来表示表达式,树的每一个节点包括一个运算符和运算数。代数表达式中只包含,-,*,/,(,)和一位整数且没有错误。按照先括号,再乘除,后加减的规则构造二叉…

【算法设计zxd】第6章 回溯法

目录 6.1 回溯法的设计技术 : 四皇后问题 回溯法: 算法框架: 思考题: 回溯算法的适用条件 【例6-1】求满足下列不等式的所有整数解: 6.2回溯算法的经典例题 【例6-2】装载问题  问题分析 计算模型  算法设计与描…

selenium多窗口、多iframe切换、alert、3种等待

1、多标签/多窗口之间的切换 场景: 在页面操作过程中有时候点击某个链接会弹出新的窗口,这时就需要切换到新打开的窗口上进行操作。这种情况下,需要识别多标签或窗口的情况。 操作方法: switch_to.window()方法:切换…

【AFL学习笔记(一)】简单的使用AFL进行漏洞挖掘测试

首先声明一点,ALF都是在Linux系统上运行 本文使用的是Ubuntu 20.4 版本进行演示 Step 1 下载afl-2.52b 官网地址afl2.52b 直接下载地址直接下载地址 下载完成之后在Ubuntu系统上进行解压: tar -afl-2.52b.tgzStep 2 创建测试用例 ①:创…

YOLOv5-训练自己的VOC格式数据集(VOC、自建数据集)

YOLOv5:训练自己的 VOC 格式数据集 1. 自定义数据集 1.1 环境安装 pip install -r requirements.txt -i https://pypi.tuna.tsinghua.edu.cn/simple注意: 安装 lxmlPillow 版本要低于 10.0.0,解释链接: module ‘PIL.Image’ has no attri…

Amazon图片下载器:利用Scrapy库完成图像下载任务

概述 本文介绍了如何使用Python的Scrapy库编写一个简单的爬虫程序,实现从Amazon网站下载商品图片的功能。Scrapy是一个强大的爬虫框架,提供了许多方便的特性,如选择器、管道、中间件、代理等。本文将重点介绍如何使用Scrapy的图片管道和代理…

vue 使用crypto.js解密后,用JSON.parse转义报错非空白格解决办法

问题: 用JSON.parse转义crypto解密后的json字符串会发生错误。如图: 原因: 那是因为crypto自己加了一些未可见的字符,所以用正常的JSON.parse(xxxx)会报错。 解决办法: JSON.parse(xxxx.replace(/[\u0000-\u001F\u…

TX Text Control.NET 32.0 For WPF

TX Text Control 支持VISUAL STUDIO 2022、.NET 5 和 .NET 6 支持 .NET WPF 应用程序的文档处理 将文档编辑、创建和 PDF 生成添加到您的 WPF 应用程序中。 视窗用户界面 功能齐全的文档编辑器 TX Text Control 是一款完全可编程的丰富编辑控件,它在专为 Visual Stu…

C++入门篇---(完)内联函数,auto,for,nullptr

往期回顾: ⭐C入门篇---(1)命名空间与缺省参数 ⭐C入门篇---(2)函数重载 ⭐C入门篇---(3)引用 目录 1.内联函数 1.1概念 1.2特性 2.aotu关键字 2.1类型别名 2.2auto简介 2.3auto使用细节 2.4auto不能推导的场景 3.范围for 3.1语法 3.2使用条件 4.指针空值(nullptr) …

C#中List、Dictionary、HashSet用法以及区别

前言 在C#编程中,List、Dictionary和HashSet是常用的集合类型,它们都有自己的特点和适用场景。本篇博客将介绍它们的用法、区别及常见操作。深入了解这些集合类型,能够帮助我们更好地组织和处理数据。 1. List: List是一个有序可重复集合,可…

【AI视野·今日CV 计算机视觉论文速览 第269期】Tue, 17 Oct 2023

AI视野今日CS.CV 计算机视觉论文速览 Tue, 17 Oct 2023 Totally 158 papers 👉上期速览✈更多精彩请移步主页 Daily Computer Vision Papers HairCLIPv2: Unifying Hair Editing via Proxy Feature Blending Authors Tianyi Wei, Dongdong Chen, Wenbo Zhou, Jing …

【腾讯云】云服务器、云数据库、COS、CDN、短信等云产品特惠热卖中

![请 https://cloud.tencent.com/act/cps/redirect?redirect2446&cps_key2e531299bf7e92946df4c3162a81b552&fromconsole

【故障诊断】用于轴承故障诊断的候选故障频率优化克改进包络频谱研究(Matlab代码实现)

💥💥💞💞欢迎来到本博客❤️❤️💥💥 🏆博主优势:🌞🌞🌞博客内容尽量做到思维缜密,逻辑清晰,为了方便读者。 ⛳️座右铭&a…

网络编程 - TCP协议

一,TCP基本概念 TCP的特性: TCP是有连接的:TCP想要通信,就需要先建立连接,之后才能通信 TCP是可靠传输:网络上进行通信,A给B发消息,这个消息是不可能做到100%送达的,所以…

Qt配置OpenCV(保姆级教程)

Qt配置OpenCV Qt下载CMake安装OpenCV安装Qt配置OpenCV Qt下载 Qt点击下载 具体的安装过程就不在讲了,根据自己的需求进行安装。 CMake安装 CMake点击下载 直接跟着提示进行安装就行。 OpenCV安装 OpenCV点击下载 提示:这里建议安装我指定的版本&#x…

关于python环境下的语音转文本,whisper或funASR

因为前阵子,有需求要将语音转为文本再进行下一步操作。感觉这个技术也不算是什么新需求,但是一搜,都是大厂的api,或者是什么什么软件,由于想要免费的,同时也要嵌入在代码中,所以这些都不能用。、…

半导体可靠性测试方法都有哪些?

半导体测试是半导体设备中的一种技术,其中半导体组件(芯片、模块等)在组装到系统就会出现故障。在特定电路的监控下,部件被迫经历一定的半导体试验条件,并分析部件的负载能力等性能。这种半导体测试有助于确保系统中使用的组件导体器件&#…

JDK命令行工具

1 jps: jps命令可以方便的查看进程id,启动类,传入参数, jvm参数 jps命令类似于linux 下的ps,但是只列出java的进程. 直接运行jps不加参数,会列出java程序的进场ID,及main函数名称 C:\Users\shj>jps 42340 Jps 41064 42040 JucApplication 37804 Launcher可以看到,目前有4个…

Confluence 用户管理

1. 创建用户 功能入口: Confluence→管理→用户管理→添加用户 功能说明: 填写必要信息,点击“添加”按钮,即可完成用户创建 用户名:英文名称,真实用户统一采用邮箱前缀;全名:中…