简体   繁体   English

C:包含动态分配的成员的结构的范围?

[英]C: Scope of a struct that contains dynamically allocated member?

I have a struct and a function that returns an instance of Foo defined as follows: 我有一个结构和一个函数,返回一个Foo实例,定义如下:

struct Foo
{
    int a;
    int* b;     
};

struct Foo makeFoo(int a, int bSize)
{
    struct Foo foo;
    foo.a = a;
    foo.b = malloc(sizeof(int) * bSize);
    for (int i = 0; i < bSize; ++i)
        foo.b[i] = i;

    return foo;
}

Initially, I thought foo is a local variable and it'll be gone when makeFoo returns, but from this question Is it safe to return a struct in C or C++? 最初,我以为foo是一个局部变量,当makeFoo返回时makeFoo消失,但是从这个问题makeFoo用C或C ++返回结构是否安全? , I know that it's safe to do so. ,我知道这样做是安全的。

Now my question is when will memory for foo be collected? 现在我的问题是,何时会收集foo内存? Do I have to free its b member first? 我必须先freeb成员吗?

Let's say I use makeFoo like this: 假设我像这样使用makeFoo

void barFunc()
{
    struct Foo foo = makeFoo(3, 10);

    printf("Foo.a = %d;\nFoo.b = [", foo.a);
    for (int i = 0; i < 10; ++i)
        printf("%d, ", foo.b[i]);

    printf("\n");
}

void main(int argc, char* argv)
{
    barFunc();  
}

When barFunc returns and I'm back in main , is memory for foo collected yet? barFunc返回并且我回到main ,是否收集了foo内存? Or do I have to call free(foo.b) at the end of barFunc ? 还是我打电话free(foo.b)在结束barFunc

Initially, I thought foo is a local variable and it'll be gone when makeFoo returns, but from this question Is it safe to return a struct in C or C++?, I know that it's safe to do so. 最初,我以为foo是一个局部变量,当makeFoo返回时它将消失,但是从这个问题出发,用C或C ++返回结构是否安全?我知道这样做是安全的。

You do realize the local foo indeed is gone? 确实意识到本地foo确实消失了吗? returning a struct by value as you do here just copies its contents to the instance provided by the caller.(*) 如您在此处按值返回struct ,只是将其内容复制到调用方提供的实例中。(*)

But, of course, the contents include a pointer pointing to some memory you allocated with malloc() . 但是,当然,内容包括一个指针,该指针指向您使用malloc()分配的某些内存。 So it has to be free() d later. 因此它必须在以后free() d。

(*) This can be a good idea for small structs, depending on your needs, but always keep in mind the whole contents are copied -- it's definitely not what you want for a somehow large struct. (*)对于小型结构,这可能是个好主意,具体取决于您的需求,但请始终记住要复制整个内容-绝对不是大型结构所需要的。

You have to call free(foo.b) by yourself before the foo variable in barFunc goes out of scope. barFuncfoo变量超出范围之前,您必须自己调用free(foo.b) This is not necessary in the makeFoo function because foo and the pointer to the allocated memory is copied to the caller, so it's all right. makeFoo函数中这不是必需的,因为foo和指向已分配内存的指针已复制到调用方,因此可以。

Since you have a makeFoo function, it would be good practice to have a deleteFoo function too: 由于您具有makeFoo函数,因此最好也具有deleteFoo函数:

void deleteFoo(struct Foo *foo)
{
  free(foo->b);
}

void barFunc()
{
  struct Foo foo = makeFoo(3, 10);
  ...
  deleteFoo(&foo);
}

Yes it Is it safe to return a struct from a C/C++ function, but struct with large static data as struct fooo{int a[1024*1024*1024];}; 是的,从C / C ++函数返回结构是安全的,但是具有大量静态数据的struct fooo{int a[1024*1024*1024];};作为struct fooo{int a[1024*1024*1024];}; can cause program to crash. 可能导致程序崩溃。 so it is much safer to return a pointer to an allocated block of memory for similar structs. 因此,将指针返回到类似结构的已分配内存块要安全得多。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM