定义一个具有结构参数的宏

huangapple go评论62阅读模式
英文:

Defining a Macro having struct argument

问题

我有一个名为Row的结构体:

```c
typedef struct
{
    uint32_t id;
    char username[COLUMN_USERNAME_SIZE];
    char email[COLUMN_EMAIL_SIZE];

} Row;

此外,我还定义了一个宏:

#define size_of_attribute(Struct, Attribute) sizeof(((Struct *)0)->Attribute)

// 每个属性的大小
const uint32_t ID_SIZE = size_of_attribute(Row, id);
const uint32_t USERNAME_SIZE = size_of_attribute(Row, username);
const uint32_t EMAIL_SIZE = size_of_attribute(Row, email);

为什么在定义size_of_attribute宏时要使用空指针来获取结构体Row中每种数据类型的大小?是否有其他表达上述宏的方式?


<details>
<summary>英文:</summary>

I have a struct named Row :

typedef struct
{
uint32_t id;
char username[COLUMN_USERNAME_SIZE];
char email[COLUMN_EMAIL_SIZE];

} Row;


Also, I have defined a Macro :

#define size_of_attribute(Struct, Attribute) sizeof(((Struct *)0)->Attribute)

// size of each attributes
const uint32_t ID_SIZE = size_of_attribute(Row, id);
const uint32_t USERNAME_SIZE = size_of_attribute(Row, username);
const uint32_t EMAIL_SIZE = size_of_attribute(Row, email);


Why are we using a null pointer while defining the size_of_attribute Macro to get the size of each data
type in the struct Row? Is there any other way to express the above Macro?

</details>


# 答案1
**得分**: 3

为什么在定义 `size_of_attribute` 宏以获取结构体 `Row` 中每种数据类型的大小时要使用空指针?

因为:
* 您没有(或不需要)`Row` 的实例
* 在 `sizeof 表达式` 中,表达式不会被评估。它处于“未评估的上下文”中。解引用一个 `NULL` 指针会导致未定义的行为,但由于这个表达式没有被评估,因此实际上没有解引用 `NULL` 指针,所以是安全的。

还有其他表达上述宏的方式吗?

您可以使用类似的结构,假装实际上创建了一个 `Struct`:
```c
#define size_of_attribute(Struct, Attribute) (sizeof (Struct){}.Attribute)

同样,由于sizeof后面的表达式没有被评估,它实际上并不会创建一个 Struct

英文:

> Why are we using a null pointer while defining the size_of_attribute Macro to get the size of each data type in the struct Row?

Because:

  • You don't have (or need) an instance of Row
  • In sizeof expression the expression is not evaluated. It is in an "unevaluated context". Dereferencing a NULL pointer causes undefined behavior, but since this expression is not evaluated, the NULL pointer is not actually dereferenced and it's therefore safe.

> Is there any other way to express the above Macro?

You could use a similar construct, pretending to actually create a Struct:

#define size_of_attribute(Struct, Attribute) (sizeof (Struct){}.Attribute)

Again, since the expression after sizeof is not evaluated, it doesn't actually create a Struct.

huangapple
  • 本文由 发表于 2023年6月16日 00:46:42
  • 转载请务必保留本文链接:https://go.coder-hub.com/76483855.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定