c语言 - 为什么不需要释放静态数组?



我想知道为什么不需要释放静态数组?我知道在创建动态阵列时,例如

int *p;
p = malloc(10*sizeof(int));

我们必须使用释放分配的内存

free(p);

对于函数中的静态数组,当调用的函数完成时,静态数组将自动释放。

我不明白的是:当使用这样的函数返回静态数组时:

int *subFunc(){
    static int a[5] = {1,2,3,4,5};
    return a;
}
int main(){
    int *p;
    p = subFunc();
}

如果静态数组在执行完成后自动释放,那么我们如何才能正确访问静态数组的值?

如果静态数组在执行完成后自动释放,那么我们如何才能正确访问静态数组的值

不,不是那样的。CCD_ 1变量在启动CCD_ 2之前被初始化,并且其生存期是程序的整个执行。因此,它们可以从函数(定义它们的函数)中return导出,并且仍然可以访问。它们不是本地(对于函数),当函数完成执行时,这将超出生存期。

相关,引用C11第6.2.4章

一个对象,其标识符是在没有存储类说明符的情况下声明的_Thread_local,以及具有外部或内部链接或具有存储类说明符static具有静态存储持续时间。它的生命周期是程序及其存储值在程序启动之前只初始化一次。

关于函数内static变量的范围,是的,它仅限于函数本身,如第6.2.1章中所述

[…]如果声明符或类型说明符声明该标识符显示在块内或中的参数声明列表中函数定义,标识符具有块作用域,块作用域终止于关联块。[…]

这意味着,很明显,不能在subFunc()之外使用数组a,因为static0在subFunc()之外是不可见的。

但是,当您对数组进行return(返回数组会导致指向数组第一个元素FWIW的指针衰减)时,由于static数组的生命周期是程序的整个执行过程,因此访问返回的指针(当然,在边界内)是完全有效和合法的。

静态变量即使在它们所在的块之后仍然存在被定义为终止。因此函数在对同一函数的重复函数调用之间保留作用静态自动变量的范围与自动变量的,即它是所在块的本地变量定义但是,为节目的持续时间。静态变量可以在声明;初始化器必须是常量表达式,并且当内存为分配给静态变量。-源

当控制从该函数中出来时,静态数组或变量将不会被释放。

静态变量的作用域是声明它的函数的局部,但其生存期在整个程序中。

对于子函数中的静态数组,当调用的子函数完成时,静态数组将自动释放。

这不是真的。静态数组不会在您进入函数时创建,也不会在您离开函数时销毁。

静态变量及其内部的数据非常像全局变量!函数唯一的本地属性是名称。(你会听到人们谈论变量的"范围"——这意味着"我可以在哪里使用这个名称来引用它。")

因此,当你考虑静态数组的寿命时,你可以在脑海中替换:

int *subFunc(){
    static int a[5] = {1,2,3,4,5};
    return a;
}

带有

int ONLY_USE_ME_INSIDE_SUBFUNC__a[5] = {1,2,3,4,5};  /* global variable */
int *subFunc(){
    int * a = ONLY_USE_ME_INSIDE_SUBFUNC__a;  /* a is the same as the global */
    return a;
}

然后假装你的程序中没有其他人能接触到这个全局变量。

我想知道为什么不需要释放静态数组?

  1. 内存管理函数(malloc、calloc)未分配的内容,如int a[5],无需明确负责释放

  2. 静态变量,如static int a[5],用于在本地范围内访问(它们在本地函数的后续调用之间保留其值)。它们是在编译时创建的,正是为了这个目的,它们有一个程序生存期,所以释放它们不是一个合乎逻辑的考虑,即使这是可能的,这不是

  3. 其他一切都在其他答案中得到了巧妙的解释。

函数内的Static variables,通常用于通过多次调用来维护函数范围内的一些数据。它们在main()之前初始化,它们的生存期是程序的整个执行期。因此,如果它们在退出函数后被释放,那就没有意义了。如果释放它们,下次调用函数时就会崩溃,因为它们不会被引用。

最新更新