如果我们在SomeFunction
内定义一个数组,它在其作用域中是有效的。但它到底存放在哪里呢?局部变量通常存储在堆栈上,但我问自己是否整个数组都存储在堆栈上,或者仅仅是指向数据字段的指针,数据实际上存储在那里(比如调用malloc在堆上分配内存)。浅谈单片机的实现。
所以这个问题也引出了另一个问题。如果数据存储在堆中,如果指针将被保存到pdata
并在不同的作用域(SomeOtherFunction
)中访问,则该操作是否有效?数据是否可以在那里使用,或者我如何知道数据是否不再有效?
#define DATAFIELDLEN 127
static uint8_t* pdata;
static void SomeFunction()
{
uint8_t dataField[DATAFIELDLEN] = {};
// Write some stuff to the datafield
pdata = dataField; // Save pointer to the datafield
}
static void SomeOtherFunction()
{
// Use datafield here
for(uint8_t ii=0; ii<DATAFIELDLEN; ii++){
// Dereference Data here
someOperation(pdata[ii]); // <-------- is the data valid here?
}
}
void main()
{
SomeFunction();
SomeOtherFunction();
}
另一种可能是将该文件全局范围内的datafield定义为
static
。然后将数据存储在初始化为零的数据中,并在整个文件中有效。但是在我提出的方法中,我想通过不让这个数据字段一直可用来节省一些内存空间。或者还有其他有用的做法吗? 最佳答案
不,那里的数据无效。你可以让它有效,但它真的很危险。让我解释一下。
当您在SomeFunction()
中分配数组时,它是在堆栈上分配的。这意味着,一旦您从该函数返回,内存将在将来某个时候随着堆栈的使用而被覆盖。将指针解引用到实际上无法控制的内存区域。有时你可能会逃脱惩罚,但这绝对是一种未定义的行为。
另一方面,虽然实际上并不建议,但您可以将该数组标记为static
。如果您这样做了,它将不再在堆栈上分配,当它超出范围时,您可以继续访问它。请明确,我不推荐这是一个好的解决方案。
使这个保持有效的正确方法是malloc()
它的内存并用pdata
指向它。
关于c - 本地定义的数组在其定义的功能之外是否有效?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/35483484/