簡體   English   中英

使用sizeof分配結構指針的正確方法是什么?

[英]what's the correct way to malloc struct pointer using sizeof?

想象一下,我有以下結構

struct Memory {
    int type;
    int prot;
};

typedef struct Memory *Memory;

如何使用malloc()初始化它?

Memory mem = malloc(sizeof(Memory));

要么

Memory mem = malloc(sizeof(struct Memory));

分配它的正確方法是什么?

您的struct聲明有些混亂,並且typedef在許多級別上都是錯誤的。 這是我的建議:

//typedef + decl in one
typedef struct _memory {
    int type;
    int prot;
} Memory;

然后像這樣分配:

Memory *mem = malloc(sizeof *mem);

像這樣讀取malloc調用: “分配存儲mem指向的任何類型所需的內存量” 如果將Memory *mem更改為Memory **mem ,它將分配4或8個字節(取決於平台),按目前的情況,它可能會分配8個字節,具體取決於int的大小以及編譯器的填充方式有關詳細信息和示例,請參見 struct check Wiki

通常認為使用sizeof *<the-pointer>是分配內存的更好方法,但是如果需要,可以編寫:

Memory *mem = malloc(sizeof(Memory));
Memory *mem = malloc(sizeof(struct _memory));

他們都做同樣的事情。 請注意,如果您typedef一個結構的定義,那可能是因為您想要抽象某些東西的內部工作原理,並想要編寫各種API。 在這種情況下,您應該盡可能不鼓勵使用struct _memory ,而應該使用Memory*<the-pointer>

如果要typedef指針,則可以編寫以下代碼:

typedef struct _memory {
    int type;
    int prot;
} *Memory_p;

在這種情況下:

Memory_p mem = malloc(sizeof *mem);

可能看起來與直覺相反,但是正確的,如下所示:

Memory_p mem = malloc(sizeof(struct _memory));

但是這個:

Memory_p mem = malloc(sizeof(Memory_p));

是錯誤的(它不會分配該結構所需的內存,而是存儲指向它的指針的內存)。

也許這是個人喜好的問題,但是我個人認為typedef掩蓋了某些東西。 在許多情況下,這樣做是更好的選擇(例如FILE* ),但是一旦API開始隱藏您正在使用指針的事實,我就開始擔心。 它傾向於使代碼更難閱讀,調試和記錄...

只是這樣想:

int *pointer, stack;

*運算符會修改給定類型的變量,指針typedef會同時執行這兩種操作。 那只是我的看法,我敢肯定,有很多使用指針typedef的程序員比我熟練得多。
但是,在大多數情況下,指針typedef會附帶自定義分配器函數或宏,因此您不必編寫看起來很奇怪的語句,例如Memory_p mem = malloc(sizeof *mem); ,但是您可以編寫ALLOC_MEM_P(mem, 1); 可以定義為:

#define ALLOC_MEM_P(var_name, count) Memory_p var_name = malloc(count * sizeof *var_name)

或者其他的東西

 typedef struct Memory * Memory;

 Memory mem = malloc (sizeof (Memory));

錯了。 正確的方法是:

typedef struct memory
{
     int type;
     int prot;
} *MEMPTR;

要么

struct memory
{
     int type;
     int prot;
};

typedef struct memory *MEMPTR;

結構的名稱應與指向它的指針的名稱不同。

這個建築

struct {
    int type;
    int prot;
} Memory;

定義一個名稱為Memory的對象,該對象具有未命名結構的類型。

因此下一個建築

typedef struct Memory *Memory;

定義1)一種新的類型struct Memory ,與上面的定義和名稱Memory沒有共同之處。 和2)另一個新類型名稱Memory ,它是指向struct Memory指針。

如果這兩種構造都存在於同一編譯單元中,則編譯器將發出錯誤,因為typedef聲明中的名稱Memory (指針的名稱)試圖重新聲明具有相同名稱Memory的未命名結構類型的對象。

我想你是說以下

typedef struct Memory {
    int type;
    int prot;
} Memory;

在這種情況下,您可以像使用malloc一樣使用兩條記錄

Memory *mem = malloc( sizeof( Memory ) );

struct Memory *mem = malloc( sizeof( struct Memory ) );

要么

Memory *mem = malloc( sizeof( struct Memory ) );

要么

struct Memory *mem = malloc( sizeof( Memory ) );

因為現在兩個標識符Memory位於兩個不同的名稱空間中,所以第一個用於標記struct ,第二個不使用標記struct。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM