前言:
大家好! 五一过完不知道大家玩的如何呢?
博主是玩爽啦!!!知识统统忘掉啦!!
所以,本章节带大家做一个总结,复习。让知识回归大脑!
一·程序分配区域
C语言程序在运行时主要涉及以下五个关键内存区域: 代码区 、 数据区 、 堆区 、 栈区 和 常量区。
代码区:
- 定义:代码区存储程序的机器代码,即编译后的二进制指令。这部分内存通常是只读的,以防止程序意外修改自身的指令。
- 作用:CPU在执行程序时,会从代码区加载指令并依次运行。代码区的内容在程序运行期间不会改变。
- 特点:代码区通常位于内存的低地址部分,操作系统负责加载和保护该区域
数据区
- 定义:数据区分为已初始化数据区和未初始化数据区。已初始化数据区存储全局变量和静态变量,而未初始化数据区存储全局未初始化变量。
- 作用:存储程序运行时需要保留的数据,包括全局变量和静态变量。这些变量在整个程序运行期间都存在,并在程序结束时被释放。
- 特点:数据区是只读或可读写的区域,具体取决于变量是否被初始化。
堆区
- 定义 :堆区用于动态内存分配,程序员通过函数如
malloc
、calloc
、realloc
等分配内存空间,用于存储运行时需要额外分配的变量。 - 作用:动态分配的内存可以在程序运行过程中随时调整大小或释放。堆区的管理较为灵活,但如果不及时释放可能导致内存泄漏。
特点:堆区的内存分配方式类似于链表,分配和释放较为复杂,且容易产生碎片
栈区
- 定义:栈区用于存储函数调用时的局部变量、函数参数以及返回地址等信息。栈区由编译器自动分配和释放,通常在函数调用结束后立即释放。
- 作用:栈区主要用于存放生命周期较短的变量,如局部变量和形参。它支持快速分配和释放,因此非常适合处理短期数据。
- 特点:栈区的内存分配方式类似于数据结构中的栈,遵循"先进后出"的原则。栈区的大小通常较小且连续,但其容量有限,如果过度使用可能导致栈溢出。
常量区
- 定义:常量区存储程序中定义的字符串常量和其他只读数据。
- 作用:常量区中的数据通常是只读的,例如字符串字面量或符号常量。这些数据在程序运行期间不会被修改。
- 特点:常量区的数据通常位于内存的高地址部分,且在程序结束时不会被释放。
总结:
1.栈:用来存放函数的形参和函数内的局部变量。由编译器分配空间,在函数执行完后由编译器自动释放。
2.堆:用来存放由动态分配函数(如malloc)分配的空间。是由程序员自己手动分配的,并且必须由程序员使用free释放。如果忘记用free释放,会导致所分配的空间一直占着不放,导致内存泄露。
3.全局区/静态区:用来存放全局变量和静态变量。程序结束时由系统释放,分为全局初始化区和全局未初始化区;存在于程序的整个运行期间,是由编译器分配和释放的。
4.常量区:常量字符串放于此,程序结束时由系统释放。例如char *str="hello_world";则"hello_world"为文字常量,存放于文字常量区。也由编译器控制分配和释放。
5.代码区:用来存放程序的二进制代码。
分析下面代码
cs
#include <stdlib.h>
#include <string.h>
int a = 0;
char *p1;
int main()
{
int b; //栈
char arr[] = "abc";
char *p2; //栈
char *p3 = "123456";
static int c =0;
p1 = (char *)malloc(10);
p2 = (char *)malloc(20);
strcpy(p1, "123456");
return 0;
}
二·文件操作
文件又分为程序文件和数据文件
程序文件
程序文件包括源程序文件(.c)
,目标文件(windows
环境后缀为.obj
),可执行程序(windows
环境后缀为.exe
)。
数据文件
文件的内容不一定是程序,而程序运行时读写的数据,比如程序运行需要从中读取数据的文件,或者输出内容的文件。本小节讨论的是数据文件在以前各章所处理数据文件的输入输出都是以终端为对象的,即从终端的键盘输入数据,运行到显示器上。其实有时候我们会把信息输出到磁盘上,当需要的时候再从数据读取到内存中使用,这里处理的就是磁盘上的文件。
文件名
一个文件要有一个唯一的文件标识,以便用户识别和引用。 文件名包含3部分:文件路径+文件主干+文件后缀 注:文件名主干不能包含以下非法字符: \ / : * ? " < > |
例如:D:\CSDN\test.txt
文件路径:D:\CSDN\
文件主干:test
文件后缀:.txt
二进制文件和文本文件?
根据数据的组织形式,数据文件被称为文本文件或者二进制文件。
数据在内存中以二进制的形式存储,如果不加转换的输出到外存的文件,则需要在存储前转换。以ASCll
字符的形式存储的文件就是文本文件。
这个就是在VS中选择不同的打开方式结果也会不同


流
流是程序和文件之间的数据传输通道。当程序打开一个文件时,系统会创建一个流与之关联。
- 输入流:数据从外部流向程序(读取)
- 输出流:数据从程序流向外部(写入)
C语言程序在启动的时候,默认打开了3
个流:
stdin
- 标准输入流,在大多数的环境中从键盘输入,scanf函数就是从标准输入流中读取数据。stdout
- 标准输出流,大多数的环境中输出至显示器界面,printf函数就是讲信息输出到标准流中stderr
- 标准错误流,大多数的环境中输出到显示器界面。
这是默认打开了这三个流,我们使用scanf ,printf等函数就可以直接进行输入输出操作的。 stdin,stdout,stderr三个流的类型是FILE*,通常称为文件指针。 C语言中,就是通过FILE*
的文件指针;来维护流的各种操作的。
使用文件,需要用到文件指针
FILE *fp; // fp是一个指向FILE结构体的指针变量
通过fopen()
函数初始化:
cs
fp = fopen("example.txt", "r"); // r表示只读模式
if (fp == NULL) {
perror("无法打开文件");
exit(EXIT_FAILURE);
}
文件的打开与关闭
fopen()函数
cs
FILE *fopen(const char *filename, const char *mode);
·第一个为文件名filename,第二个是打开的方式mode
常用打开模式:
模式 | 描述 |
---|---|
"r" | 只读方式打开文本文件 |
"w" | 只写方式创建/覆盖文本文件 |
"a" | 追加方式打开/创建文本文件 |
"rb" | 只读方式打开二进制文件 |
"wb" | 只写方式创建/覆盖二进制文件 |
"ab" | 追加方式打开/创建二进制文件 |
"r+" | 读写方式打开文本文件 |
"w+" | 读写方式创建/覆盖文本文件 |
"a+" | 读写方式打开/创建文本文件 |
例如:
cs
FILE *pf = fopen("example.txt", "r");
fclose
是C语言中用于关闭文件的函数。
cs
FILE *fp = fopen("test.txt", "w");
if(fp == NULL) {
printf("无法打开文件\n");
return -1;
}
// 进行文件操作...
fclose(fp);