C中的malloc与数组 [英] malloc vs array in C

查看:150
本文介绍了C中的malloc与数组的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在参加公开在线课程 CS50 .我上一次演讲是关于内存分配和指针的(这两个概念对我来说绝对是新的).

所教的是malloc(10*sizeof(char))在堆上分配足够的字节以存储10个字符,并返回指向第一个字节的指针,该指针可以按如下方式保存在另一个变量中:char *x = malloc(10*sizeof(char)).要释放内存,可以使用free(x).

但是还有另一种方法可以使计算机保留足够的内存来存储10个字符,即char c[10].

  1. c上方的代码段中是否还包含char*类型的指针?
  2. char c[10]是否也像malloc一样在堆上保留内存 ?
  3. 是否有分配内存等效项的方法?
  4. char c[3] = "aaa";free(c);返回运行时错误;因此看来我无法释放使用char c[3]分配的内存.为什么会这样?

我真的很感谢为刚刚了解指针的人量身定制的答案.

解决方案

所教的是malloc(10*sizeof(char))分配足够 堆上的字节,用于存储10个字符,并返回指向 可以保存在另一个变量中的第一个字节,如下所示.要释放内存,可以使用free(x).

在堆上"是一个实现概念,而不是C语言概念. C语言本身并不关心将内存划分为具有不同特征的单独区域,实际上,任何给定的C实现实际上并不一定要这样做.

即使在入门课程中,尤其是在入门课程中,特别是在入门课程中,使用C语言概念比使用特定实现样式的概念要好.在这种情况下,相关的C语言概念是存储时间:

对象的存储持续时间决定了其生存期.有四种存储期限:静态,线程,自动和已分配.

( C2011,6.2.4/1 )

malloc()调用所分配的对象(指针x指向该对象)具有已分配"的持续时间.这意味着它的生存期一直持续到通过调用free()释放该对象为止.请注意,变量x(具有自动存储持续时间的指针)与x最初指向的对象(大小为10 char s的无类型对象)之间的区别在这里.

还有很多,但是您要深入研究标准还为时过早.不过,我发现这种特征对于解决诸如您提出的问题更有用.

但是还有另一种方法可以使计算机保留足够的内存 存储10个字符,即char c[10].

是的,是的.

  1. c上方的代码段中是否还包含char*类型的指针?

不.在该声明的范围内,标识符c指向10个char的数组.数组和指针之间有密切的关系,但是它们根本不是一回事.这是至关重要的一点,许多新的C程序员都在上面遇到了困难,所以我重复一遍:数组和指针不是同一件事.详细信息将为您提供其他答案,而您在SO上已经可以找到很多答案了.

换句话说,标识符c指定x的值可以指向的一种事物,但请记住x的(指针)的值与它指向的对象是不同的

  1. char c[10]是否也像malloc一样在堆上保留内存?

如果c的声明出现在函数内部,则它将声明具有自动存储持续时间的数组.这意味着数组的生存期将持续到标识符c超出范围为止.实现的关注点在于该阵列的存储位置,但是在提供堆/堆栈区别的实现上,存储很可能在堆栈上,而不是堆上.

  1. 是否有分配内存等效项的方法?

不. malloc()分配具有分配的存储持续时间的对象,该对象的生命周期由程序负责显式管理.另一个对象分配一个具有自动存储持续时间的对象,该对象的生存期由标识符的范围决定.

  1. char c[3] = "aaa";free(c);返回运行时错误;所以看来我无法释放用char c[3]分配的内存.为什么 是吗?

最直接的原因是free()函数的规范明确指出了

[I] f参数与内存先前返回的指针不匹配 管理功能,或者是否已通过调用释放空间 free或realloc,行为是不确定的.

( C2011,7.23.2.3/2 )

也就是说,如果您尝试释放具有自动持续时间的对象的指针,则该标准不需要运行时错误(或任何其他特定的行为),但是它明确地否认了您可以以这种方式释放内存的任何诺言. /p>

但我认为,更令人满意的答案是free()是如何用分配的存储持续时间标记对象生命周期的结束,而不是使用自动(或其他)持续时间标记对象的生命周期的结束.该对象的存储所在的位置(例如堆栈 vs.堆)是辅助的.

I am taking an open online course CS50 from Harvard. The last lecture I had was about memory allocation and pointers (two concepts which are absolutely new to me).

What was taught is that malloc(10*sizeof(char)) allocates enough bytes on the heap to store 10 characters and returns a pointer to the first byte which can be saved in another variable as follows char *x = malloc(10*sizeof(char)). To free the memory one would use free(x).

But there is another way to make a computer to reserve enough memory to store 10 characters i.e. char c[10].

  1. Is in the code snippet above c also a pointer of type char*?
  2. Does char c[10] also reserve memory on the heap as malloc does?
  3. Are the ways to allocate memory equivalent?
  4. char c[3] = "aaa";free(c); returns a runtime error; so it seems I can not free the memory I have allocated with char c[3]. Why is that?

I would really appreciate an answer tailored to somebody who just have learned about pointers.

解决方案

What was taught is that malloc(10*sizeof(char)) allocates enough bytes on the heap to store 10 characters and returns a pointer to the first byte which can be saved in another variable as follows char *x = malloc(10*sizeof(char)). To free the memory one would use free(x).

"On the heap" is an implementation concept, not a C-language concept. The C language itself is not concerned with partitioning memory into separate areas with different characteristics, and in fact it is not necessarily the case that any given C implementation in fact does so.

Even in an introductory course -- maybe especially in an introductory course -- it is better to use C language concepts than concepts native to a certain implementation style. The relevant C language concept in this case is storage duration:

An object has a storage duration that determines its lifetime. There are four storage durations: static, thread, automatic, and allocated.

(C2011, 6.2.4/1)

The object allocated by your malloc() call, (in)to which your pointer x points, has "allocated" duration. That means its lifetime lasts until that object is freed by a call to free(). Note well the distinction here between variable x, a pointer with automatic storage duration, and the object to which x initially points, an untyped object the size of 10 chars.

There is (much) more, but this point in your journey is early for delving deeply into the standard. Nevertheless, I find this characterization more useful for addressing questions such as those you pose.

But there is another way to make a computer to reserve enough memory to store 10 characters i.e. char c[10].

Yes, that's true.

  1. Is in the code snippet above c also a pointer of type char*?

No. Within the scope of that declaration, the identifier c refers to an array of 10 chars. There is a close relationship between arrays and pointers, but they are not at all the same thing. This is a crucially important point, and one over which many new C programmers stumble, so I repeat: arrays and pointers are not the same thing. The details would make for a whole other answer, however, and one which you can already find several times over here on SO.

To put it another way, identifier c designates one kind of thing to which x's value could point, but remember that x's (pointer) value is distinct from the object to which it points.

  1. Does char c[10] also reserve memory on the heap as malloc does?

If your declaration of c appears inside a function then it declares an array with automatic storage duration. This means that the array's lifetime lasts until identifier c goes out of scope. It is the implementation's concern where the storage for that array is located, but on an implementation that provides a heap / stack distinction, the storage would most likely be on the stack, not the heap.

  1. Are the ways to allocate memory equivalent?

No. malloc() allocates an object with allocated storage duration, whose lifetime the program is responsible for managing explicitly. The other allocates an object with automatic storage duration, whose lifetime is determined by the identifier's scope.

  1. char c[3] = "aaa";free(c); returns a runtime error; so it seems I can not free the memory I have allocated with char c[3]. Why is that?

Most directly, it is because the specifications for the free() function explicitly say

[I]f the argument does not match a pointer earlier returned by a memory management function, or if the space has been deallocated by a call to free or realloc, the behavior is undefined.

(C2011, 7.22.3.3/2)

That is, the standard does not require a runtime error (or any particular other behavior) if you try to free a pointer to an object with automatic duration, but it explicitly disclaims any promise that you can free memory that way.

But a more satisfying answer, I think, is that free() is how you mark the end of the lifetime of an object with allocated storage duration, not one with automatic (or other) duration. Where the storage for the object is located (e.g. stack vs. heap) is ancillary.

这篇关于C中的malloc与数组的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆