我想知道两者的区别
struct file_operations {
} a;
和
struct file_operations {
} *a;
它们在内存中是如何分配的?在第一种情况下,编译器如何知道“a”的内存位置?它来自符号表吗?如果是这样,如何找到符号表(或任何其他表)的地址?
在第二种情况下,我假设内存地址存储在一个大小为 32 位的变量中,这个变量的位置(第二个代码中“a”的地址)是如何计算出来的?
最佳答案
在第一种情况下,在内存中分配一个结构实例,分配的字节数等于 sizeof(a)
返回的值。
在第二种情况下,分配了一个指针,分配的字节数等于指针的大小,即 sizeof(void *)
。
正如您可能猜测的那样,第二种情况不允许您访问结构的字段,因为指针指向的内存无效,直到您从堆中请求足够的内存,或者直到您指向它到第一个示例中的实例。
假设我们有以下结构
struct Data {
int quantity;
double value;
char name[100];
};
如果您执行以下操作
struct Data data;
然后分配了一个struct Data
的实例,你可以立即访问它的字段,例如
data.quantity = 1;
data.value = 3.0;
strcpy(data.name, "My Name Is ...");
如果你声明一个指针,比如
struct Data *pointer;
然后你不能访问这些字段,直到你使指针指向一个有效的struct Data
实例,否则会发生未定义的行为,你可以通过获取struct Data data;
我们已经在上面初始化了,像这样
pointer = &data;
pointee 的生命周期限制了指针的有效生命周期,一旦你离开了 data
声明的范围,那么指针将指向垃圾,因为 data
将被释放。
另一种使指针有效的方法是使用 malloc()
,即通过请求 sizeof(struct Data)
从系统堆中请求内存来完成> 字节,像这里1
pointer = malloc(sizeof(struct Data));
之后,你首先检查内存是否被分配,当有问题时malloc()
保证返回一个特殊的指针NULL
,这是一个无效的指针帮助您检查 poitner
是否实际指向有效内存,
if (pointer != NULL)
{
pointer->quantity = 1;
pointer->value = 3.0;
strcpy(pointer->name, "My Name Is ...");
}
在这种情况下,指针在您决定无效之前一直有效,当您确定无效时,您必须像这样调用 free()
free(pointer);
之后,如果您再次尝试访问该指针,将发生未定义的行为。
1您还可以使用此语法使其独立于指针
的类型 pointer = malloc(sizeof(*pointer));
,因为 sizeof(*pointer)
等于 sizeof(struct Data)
。
关于c++ - 混淆结构和结构指针,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30326116/