什么时候在 C 中分配和取消分配静态和动态内存?

hil*_*ace 2 c memory memory-management

我现在正在学习 C 并试图弄清楚 C 的内存管理是如何工作的。如果我错了,请纠正我,但据我所知:

静态内存分配 - 这发生在编译时。编译器为静态内存分配必要的内存。

静态内存释放 - 当块/函数完成运行(对于局部变量)或当整个程序完成执行(对于全局变量)时,内存会自动释放。

动态内存分配 - 在运行时分配内存,因为此时输入的大小未知。

动态内存释放 - 执行 free() 时释放内存。

这是对的吗?我错过了什么吗?

Ser*_*sta 5

C 语言中有 3 种不同的存储持续时间:

  • static:变量的生命周期就是程序的生命周期。它在加载时分配(仅在编译时定义),仅在操作系统卸载程序时释放。静态变量是在任何函数之外声明的变量,以及具有static修饰符的局部变量(在函数或块中声明)
  • 自动:自动变量在块(或函数)内声明,没有存储修饰符。它们的生命周期从集团开始时开始,到集团结束时结束。它们通常在 bloc 的开头分配并在其末尾释放,但由于 if 规则,优化编译器可以更快地分配它们并稍后释放它们,例如,如果 bloc 位于循环内。
  • 动态:它们是通过手动分配的malloc,并且只会被解除分配free

常见的实现为自动变量使用系统堆栈,为动态变量使用内存池(在需要更多内存时询问操作系统),但这是一个实现细节

使用多线程时,还有第四种存储期:线程存储期。这些变量是用_Thread_local存储类修饰符声明的。它们的生命周期就是线程的持续时间,每个线程都有自己的副本。

对于常见的实现,它们的管理方式与静态变量相同:它们在创建线程时由操作系统分配,并在线程结束时回收(仍然由操作系统)。


关于你的措辞的一些评论:

静态内存分配 - 这发生在编译时。

请注意,编译时间和加载时间是不同的。在构建时只创建一个文件,内存只在运行时由系统分配

静态内存释放 - 当块/函数完成运行时,内存会自动释放(对于局部变量)...

范围(本地与全局)和存储持续时间之间存在混淆。一个函数可以包含静态变量,这是static关键字的原因之一

动态内存分配——在运行时分配内存,因为此时输入的大小是未知的

这是程序员使用动态内存的一个可能原因,但可能还有其他原因,例如因为这样代码会更清晰。特别是,当您想模拟 C 语言中的面向对象编程时,动态内存是一个很好的工具。