C 这个显式堆或堆栈是动态的吗?

C 这个显式堆或堆栈是动态的吗?,c,memory,memory-management,C,Memory,Memory Management,给定以下C语言代码段: int* x; x = (int *) malloc(40); 我们知道这是一个显式的堆动态分配 如果我将代码更改为: int* x = (int *) malloc(40); 它仍然是显式堆动态的吗?我的朋友认为这是一个堆栈动态,但我认为这是一个显式堆动态,因为我们从堆中分配内存 显式堆动态定义为由程序员编写的显式运行时指令分配和释放的变量。这难道不意味着任何malloc/calloc调用都是显式堆吗 编辑:我和我的教授谈过,她为我澄清了一些事情 当我们宣布 ch

给定以下C语言代码段:

int* x;
x = (int *) malloc(40);
我们知道这是一个显式的堆动态分配

如果我将代码更改为:

int* x = (int *) malloc(40);
它仍然是显式堆动态的吗?我的朋友认为这是一个堆栈动态,但我认为这是一个显式堆动态,因为我们从堆中分配内存

显式堆动态定义为由程序员编写的显式运行时指令分配和释放的变量。这难道不意味着任何malloc/calloc调用都是显式堆吗


编辑:我和我的教授谈过,她为我澄清了一些事情

当我们宣布

char * str = (char *) malloc(15);

我们说str是数据类型char-pointer,并且具有堆栈动态存储绑定。然而,当我们引用str引用的对象时,我们说它是显式堆动态的

是,
malloc
在堆上分配请求的内存。堆内存用于增长和收缩的动态数据结构。

来自标准

任何指针类型都可以转换为整数类型。除非前面指定,否则结果是实现定义的如果结果不能用整数类型表示,则行为未定义。结果不必在任何整数类型的值范围内

这说明了为什么指针的类型应该是
int*
。此外,不需要强制转换-
void*
int*
的转换将在此处隐式完成

另外,为什么您认为声明带有或不带有初始值设定项的变量会影响
*alloc
及其友元函数分配的内存的存储时间。事实并非如此


有趣的是,
x
具有自动存储持续时间(通常使用堆栈实现),但它包含的内存(是的,
x
的类型将是
int*
)-它将具有分配的存储持续时间。问题是堆/堆栈不是C标准指定或提到的东西。大多数实现通常使用heap来实现分配的存储持续时间。

首先,如果要将
malloc
的结果存储在变量中,则将其正确地声明为指针,而不是int。 将malloc结果存储在int中的问题是,您可能会截断指针,并在稍后取消引用时将其放大。例如,如果在64位系统上运行该表达式,malloc将返回一个8字节的指针。但由于您将其分配给一个4字节的int,因此它会被截断。不太好

您的代码应该如下所示:

int* x = (int*)malloc(bla);
无论如何,int指针
x
本身存储在堆栈上。但不要把两者混淆。X本身是堆栈上的指针,但它指向堆上分配的内存

注:

32位应用程序(通常)有4字节指针


64位应用程序(通常)有8字节指针。

为什么要强制转换malloc的返回?标准中没有所谓的heap。heap dynamic和stack dynamic?我很困惑。“堆栈动态”和“堆动态”就我所知不是标准术语。你应该假定分配给
int*x
,而不是
int x
——将指针存储在整数中不是一个好主意。我实际上是在问这个问题(如果使用初始值设定项声明变量会影响存储持续时间),因为我正在从类中查看幻灯片,其中有一个示例[int*dist=malloc(sizeof(int)*n);]。根据幻灯片,这是堆栈动态的,堆栈动态变量是指针。感谢您指出malloc的错误示例。我将编辑这个问题。@Katrina:如果您的情况是在堆上实现分配存储,那么它将被堆分配。我想我的困惑在于,我认为由于emory被分配为堆,这一定意味着指针是“堆动态的”.但正如@C Johnson所指出的,int指针存储在堆栈上,它指向由堆分配的内存。@Katrina:这就是我所说的。变量本身具有自动存储持续时间,但如果在堆中分配,它包含的内存地址-它是堆内存的地址。Hmmm。“64位应用程序有8个字节指针。"这并不完全是一个真理。N位应用程序通常指目标处理器的本机整数大小。这通常会影响
int
long
大小的选择。指针大小是次要的,可能与N位应用程序大小或
int
/
long
大小不匹配。此外:函数指针大小可能与对象指针大小。很多可能性。好的,我澄清了。