当前位置: 首页 > news >正文

Linux笔记 --- 内存管理

        在程序中我们访问的内存地址都是从物理内存上映射而来的虚拟地址,假设我们使用的计算机实际物理内存(PM)只有1GB,而Linux中执行着三个进程,Linux会将PM中的某段内存映射成三段4G大小相同的虚拟内存(VM),让每个进程都认为得到了需要的完整内存

进程内存布局

        在虚拟内存中内存是被分配给不同的部分的,具体每部分存储的内容如下图

对该图做几点说明:

1,栈中的环境变量和命令行参数在程序一开始运行之时就被固定在了栈底(即紧挨着内核的地方),且在进程在整个运行期间不再发生变化,假如进程运行时对环境变量的个数或者值做了修改,则为了能够容纳修改后的内容,新的环境变量将会被拷贝放置到堆中。

2,栈还有一个名称叫做“堆栈”,这是中文比较奇葩的地方:“堆栈”跟“堆”没有半毛钱关系。

3,栈和堆都是动态变化的,分别向下和向上增长,大小随着进程的运行不断变大变小。

4,静态数据指的是:所有的全局变量,以及static 型局部变量。

5,数据段的大小在进程一开始运行就是固定的,其中.rodata存放程序中所有的常量,.data存放所有的静态数据,而如果静态数据未被初始化,则程序刚开始运行时系统将会自动将他们统统初始化为0然后放置在.bss段中,这么做的原因是要节省磁盘存储空间:由于未初始化的静态数据在运行时一概会被初始化为0,因此在程序文件中就没有必要保存任何未初始化的变量的值了

6,如果没有一个极具说服力的理由,我们应该尽量避免使用静态数据,因为滥用静态数据至少有两个缺点:第一,静态数据的生命周期跟整个进程相当,也就是说不管你什么时候需要用到他们,他们在进程一开始运行的时候就已经存在了,而且就算你不再需要他们,在进程完全退出之前他们都不会释放,会无条件地一直占用内存。第二,静态数据中的全局变量是一种典型的共享资源,尤其在多线程程序中,共享资源是滋生“竞态”的温床(详见5.x.x小节),实在没办法要在多线程程序在使用全局变量,必须仔细地使用各种同步互斥手段保护他们,而不是简单粗暴地胡乱使用。

7,用户代码所在的.text段也称为正文段,.text是一个默认的名称,他将会囊括用户定义的所有的函数代码,实际上我们可以将某些指定的函数放置到自己指定段当中去,比如在程序代码中有一段音乐数据,我们可以将此段数据放置在一个.mp3的代码段当中(详见2.6.3小节),而.init段是存放的系统初始化代码,这部分代码之所以要放置在.init段是因为这个段当中的代码默认只会被执行一遍(初始化只能执行一遍),完成任务之后所占据的内存会被立即释放,以便节省系统资源,因此我们自己定义的函数如果也是在进程开始之初只执行一遍就不再需要,那么也可以将之放置在该段中。

堆(heap)

        堆内存被称为内存中的自由区,这是一个非常重要的区域,因为在此区定义的内存的生命周期我们是可以控制的域,对比其他区域的内存则不然,比如栈内存,栈的特点就是临时分配临时释放,一个变量如果是局部变量,他就会被定义在栈内存中,一旦这个局部变量所在的函数退出,不管你愿不愿意该局部变量也就会被立即释放,再如静态数据,他们都被存储在数据段,如前所述,这些变量将一直占用内存直到进程退出为止。

        堆内存的生命周期是:从malloc( )/calloc( )/realloc( )开始,到free( )结束,其分配和释放完全由我们开发者自定义,这就给了我们最大的自由和灵活性,让程序在运行的过程当中,以最大的效益使用内存。

        对堆操作的函数介绍如下

 堆最大的特点是自定义其生命周期,除了调用free(),不会因为所在函数退出而释放

此处增加一个示例表明使用方法

#include <stdio.h>
#include <stdlib.h>int *heap_array(int *old_ptr,int n);
void show(int *ptr);int main(int argc, char const *argv[])
{int n , *p = (int*)malloc(1 * sizeof(int));//分配一块int类型大小的内存p[0] = 1;while (1){if(scanf("%d",&n) == 0)//输入非数字则退出break;p = heap_array(p , n);//输入数字则扩展内存并将数字填入最新的堆show(p);}free(p);return 0;
}int *heap_array(int *old_ptr,int n)
{int size,*new_ptr;size = old_ptr[0]+1;new_ptr =(int*) realloc(old_ptr , size * sizeof(int));new_ptr[0] = size;new_ptr[size - 1] = n;return new_ptr;
}void show(int *ptr)
{printf("---> ");for (int i = 1; i < ptr[0]; i++){printf("%d ",ptr[i]);}printf("<---\n");}

相关文章:

Linux笔记 --- 内存管理

在程序中我们访问的内存地址都是从物理内存上映射而来的虚拟地址&#xff0c;假设我们使用的计算机实际物理内存&#xff08;PM&#xff09;只有1GB&#xff0c;而Linux中执行着三个进程&#xff0c;Linux会将PM中的某段内存映射成三段4G大小相同的虚拟内存&#xff08;VM&…...

树莓派通过webRTC进行视频流传输到公网

为了实现树莓派和浏览器之间的视频流传输&#xff0c;你需要在公网服务器上运行 Node.js 的信令服务器&#xff0c;同时在树莓派上运行 Node.js 客户端代码。以下是具体的步骤和说明&#xff1a; 1. 公网服务器 安装 Node.js&#xff1a;在公网服务器上&#xff0c;你需要安装…...

【数据结构与算法】循环队列

循环队列 一.循环队列的引入二.循环队列的原理三.循环队列判断是否为满或空1.是否为空2.是否为满 四.循环队列入队五.循环队列出队六.循环队列的遍历七.循环队列获取长度八.总结 一.循环队列的引入 还记得我们顺序队列的删除元素嘛,我们有两种方式,一种是将数组要删除元素后面…...

为什么推荐使用@RequiredArgsConstructor代替@Autowired?

首先说一下前提&#xff1a; 项目中已经使用了Lombok&#xff0c;否则添加 Lombok 可能会增加项目的复杂度和构建时间。如果依赖项是可选的或可能在运行时改变&#xff0c;则使用字段注入或 setter 注入可能更为合适。 正文&#xff1a; 在 Spring 框架中&#xff0c;Autowir…...

ARM系列运行异常排查

一、断点指令BKPT BKPT指令产生软件断点中断&#xff0c;可用于程序的调试。它使处理器停止执行正常指令&#xff08;使处理器中止预取指&#xff09;而进入相应的调试程序。 BKPT指令的格式为&#xff1a;BKPT 16位的立即数 二、使用BKPT进行软件异常定位 假设异常发生后…...

Hive3:库操作常用语句

1、创建库 create database if not exists myhive;2、选择库 use myhive;3、查看当前选择的库 SELECT current_database();4、查看库详细信息 desc database myhive;可以查看数据文件在hdfs集群中的存储位置 5、创建库时制定hdfs的存储位置 create database myhive2 …...

C语言实现:C51单片机驱动LCD屏幕显示字符串(Proteus+Keil)

在Proteus中绘制电路原理图 我使用的版本是Protues8.16 ,Protues特别擅长仿真单片机及其外围设备&#xff0c;支持多种类型的微控制器&#xff0c;如8051、HC11、PIC、AVR、ARM、MSP430等&#xff0c;也可以设计pcb板&#xff0c;还能3D建模 1.新建工程 在 Start 栏中点击 …...

暄桐好作业之《临沈周〈东庄图册〉局部》

暄桐是一间传统美学教育教室&#xff0c;创办于2011年&#xff0c;林曦是创办人和授课老师&#xff0c;教授以书法为主的传统文化和技艺&#xff0c;皆在以书法为起点&#xff0c;亲近中国传统之美&#xff0c;以实践和所得&#xff0c;滋养当下生活。      其中“暄桐好作…...

Qt3D创建3D物体步骤

使用Qt3D接口创建3D物体的步骤大致有以下几步: 1.创建一个3D窗口 2.创建根实体 3.创建物体实体,父指针为根实体 4.创建立体图形,即物体网格,设置物体的属性 5.给立体图形添加材质,添加坐标位置,添加纹理,添加其他效果 6.创建摄像头,设置摄像头的属性,父指针为根…...

UDP程序设计

UDP协议概述 UDP&#xff0c;User Datagram Protocol&#xff0c;用户数据报协议&#xff0c;是一个简单的面向数据报(package-oriented)的传输层协议&#xff0c;规范为&#xff1a;RFC 768。 UDP提供数据的不可靠传递&#xff0c;它一旦把应用程序发给网络层的数据发送出去…...

计算机网络—电路、分组、报文交换—图文详解

计算机网络—电路、分组、报文交换 计算机网络中的数据传输方式可以根据数据的处理方式和网络资源的使用方式分为电路交换、分组交换和报文交换三种类型。 这些方式在网络设计和数据传输过程中起到了不同的作用和效果。 1. 电路交换&#xff08;Circuit Switching&#xff0…...

linux下交叉编译licensecc

本文章只做个人笔记用 下载地址&#xff1a; #https://github.com/open-license-manager/licensecc.git #下面地址下不下来就是用第一个去官网下载git clone --recursive https://github.com/open-license-manager/licensecc.git 编译前准备3个库&#xff1a;openssl&#x…...

模型剪枝综述

目录 1 深度神经网络的稀疏性&#xff1a; 2 剪枝算法分类&#xff1a; 3 具体的剪枝方法包括&#xff1a; 4 剪枝算法流程&#xff1a; 5 几种常见的剪枝算法&#xff1a; 6 结构化剪枝和非结构化剪枝各有其优缺点&#xff1a; 7 剪枝算法对模型精度的影响 8 影响剪枝…...

破解监控难题,局域网电脑监控软件哪家强?

现在的环境&#xff0c;企业要想茁壮成长&#xff0c;员工的高效工作那可是关键中的关键。但不少老板都发现了一个头疼的问题&#xff0c;员工上班老是偷懒&#xff0c;这可怎么行&#xff1f;今天&#xff0c;就来给大家详细说道说道几款出色的局域网电脑监控软件&#xff0c;…...

Linux--Socket编程TCP

前文&#xff1a;Socket套接字编程 TCP的特点 面向连接&#xff1a;TCP 在发送数据之前&#xff0c;必须先建立连接。可靠性&#xff1a;TCP 提供了数据传输的可靠性。面向字节流&#xff1a;TCP 是一个面向字节流的协议&#xff0c;这意味着 TCP 将应用程序交下来的数据看成是…...

Android Studio导入源码

在有源码并且编译环境可用的情况下&#xff1a; 1.生成导入AS所需的配置文件 在源码的根目录执行以下命令&#xff1a; source build/ensetup.sh lunch 要编译的项目 make idegen //这一步会生成out/host/linux-x86/framework/idegen.jar development/tools/idegen/idegen.sh…...

UE5 UE4 使用python进行编辑器操作

使用UE 4.25以上版本后&#xff0c;python代码改动相对较少。 如下类库在4.20/21/22等早起版本不适用&#xff0c;建议查询UE的python文档 unreal.EditorAssetLibrary 1.获取当前选中的资源&#xff08;Content中&#xff09; # 获取当前选中的资产selected_assets unreal.E…...

区块链技术在智能城市中的创新应用探索

随着全球城市化进程的加速和信息技术的快速发展&#xff0c;智能城市成为了未来城市发展的重要方向。在智能城市建设中&#xff0c;区块链技术作为一种去中心化、安全和透明的分布式账本技术&#xff0c;正逐渐展现出其在优化城市管理、提升公共服务和增强城市安全性方面的潜力…...

解决mysql事件调度器重启服务后自动失效的问题

前段时间为通过mysql事件生成测试数据&#xff0c;今天发现数据在10:57后停止了CREATE EVENT IF NOT EXISTS insert_random_data ON SCHEDULE EVERY 10 SECOND DO INSERT INTO test (createtime, random_number) VALUES (NOW(), FLOOR(RAND() * 100));检查事件状态&#…...

mybatis开启二级缓存

例子 mybatis-config.xml <configuration><settings><setting name"cacheEnabled" value"true"/></settings><environments default"development"><environment id"development"><transacti…...

synchronized 学习

学习源&#xff1a; https://www.bilibili.com/video/BV1aJ411V763?spm_id_from333.788.videopod.episodes&vd_source32e1c41a9370911ab06d12fbc36c4ebc 1.应用场景 不超卖&#xff0c;也要考虑性能问题&#xff08;场景&#xff09; 2.常见面试问题&#xff1a; sync出…...

Qt Widget类解析与代码注释

#include "widget.h" #include "ui_widget.h"Widget::Widget(QWidget *parent): QWidget(parent), ui(new Ui::Widget) {ui->setupUi(this); }Widget::~Widget() {delete ui; }//解释这串代码&#xff0c;写上注释 当然可以&#xff01;这段代码是 Qt …...

BCS 2025|百度副总裁陈洋:智能体在安全领域的应用实践

6月5日&#xff0c;2025全球数字经济大会数字安全主论坛暨北京网络安全大会在国家会议中心隆重开幕。百度副总裁陈洋受邀出席&#xff0c;并作《智能体在安全领域的应用实践》主题演讲&#xff0c;分享了在智能体在安全领域的突破性实践。他指出&#xff0c;百度通过将安全能力…...

【RockeMQ】第2节|RocketMQ快速实战以及核⼼概念详解(二)

升级Dledger高可用集群 一、主从架构的不足与Dledger的定位 主从架构缺陷 数据备份依赖Slave节点&#xff0c;但无自动故障转移能力&#xff0c;Master宕机后需人工切换&#xff0c;期间消息可能无法读取。Slave仅存储数据&#xff0c;无法主动升级为Master响应请求&#xff…...

(转)什么是DockerCompose?它有什么作用?

一、什么是DockerCompose? DockerCompose可以基于Compose文件帮我们快速的部署分布式应用&#xff0c;而无需手动一个个创建和运行容器。 Compose文件是一个文本文件&#xff0c;通过指令定义集群中的每个容器如何运行。 DockerCompose就是把DockerFile转换成指令去运行。 …...

Java求职者面试指南:计算机基础与源码原理深度解析

Java求职者面试指南&#xff1a;计算机基础与源码原理深度解析 第一轮提问&#xff1a;基础概念问题 1. 请解释什么是进程和线程的区别&#xff1f; 面试官&#xff1a;进程是程序的一次执行过程&#xff0c;是系统进行资源分配和调度的基本单位&#xff1b;而线程是进程中的…...

【学习笔记】erase 删除顺序迭代器后迭代器失效的解决方案

目录 使用 erase 返回值继续迭代使用索引进行遍历 我们知道类似 vector 的顺序迭代器被删除后&#xff0c;迭代器会失效&#xff0c;因为顺序迭代器在内存中是连续存储的&#xff0c;元素删除后&#xff0c;后续元素会前移。 但一些场景中&#xff0c;我们又需要在执行删除操作…...

2025年- H71-Lc179--39.组合总和(回溯,组合)--Java版

1.题目描述 2.思路 当前的元素可以重复使用。 &#xff08;1&#xff09;确定回溯算法函数的参数和返回值&#xff08;一般是void类型&#xff09; &#xff08;2&#xff09;因为是用递归实现的&#xff0c;所以我们要确定终止条件 &#xff08;3&#xff09;单层搜索逻辑 二…...

嵌入式面试常问问题

以下内容面向嵌入式/系统方向的初学者与面试备考者,全面梳理了以下几大板块,并在每个板块末尾列出常见的面试问答思路,帮助你既能夯实基础,又能应对面试挑战。 一、TCP/IP 协议 1.1 TCP/IP 五层模型概述 链路层(Link Layer) 包括网卡驱动、以太网、Wi‑Fi、PPP 等。负责…...

基于Uniapp的HarmonyOS 5.0体育应用开发攻略

一、技术架构设计 1.混合开发框架选型 &#xff08;1&#xff09;使用Uniapp 3.8版本支持ArkTS编译 &#xff08;2&#xff09;通过uni-harmony插件调用原生能力 &#xff08;3&#xff09;分层架构设计&#xff1a; graph TDA[UI层] -->|Vue语法| B(Uniapp框架)B --&g…...