英文:
What's the syntax of following c define?
问题
#define sigemptyset(set) (*(set) = 0, 0)
中的 , 0)
是执行两个操作:首先将 set
指向的值设为0,然后返回0。
英文:
Following snippet is from mac sdk signal.h
:
#define sigemptyset(set) (*(set) = 0, 0)
just wonder what does , 0)
do?
答案1
得分: 3
宏展开为逗号表达式:首先评估左操作数,将set
指向的对象设置为0
,然后评估右操作数,其值为整个表达式的值,因此是:0
。
换句话说,该宏的行为类似于始终成功的函数,成功由返回值0
表示。
除了类型检查外,该宏等效于:
#include <signal.h>;
int sigemptyset(sigset_t *set) {
*set = 0;
return 0;
}
请注意,<signal.h>
头文件还包含此函数的原型:
int sigemptyset(sigset_t *);
在您的代码中,调用 sigemptyset(&sigset)
调用了该宏,但您可以通过编写 (sigemptyset)(&sigset)
或者取函数指针的方式强制引用库函数。该宏允许在不改变原型的情况下进行内联扩展。clang可以在链接时对小函数进行内联扩展,但对动态库中定义的函数则不行。
相同的技巧也适用于头文件中的其他函数,对于这些函数来说,需要 , 0)
以使表达式以 int
类型评估为 0
:
#define sigaddset(set, signo) (*(set) |= __sigbits(signo), 0)
#define sigdelset(set, signo) (*(set) &= ~__sigbits(signo), 0)
#define sigemptyset(set) (*(set) = 0, 0)
#define sigfillset(set) (*(set) = ~(sigset_t)0, 0)
英文:
The macro expands to a comma expression: the left operand, evaluated first, sets the object pointed to by set
to 0
, then the right operand is evaluated and its value is the value of the whole expression, hence: 0
.
In other words, the macro behaves like a function that always succeeds, success indicated by the return value 0
.
Except for the type checking, the macro is equivalent to:
#include <signal.h>
int sigemptyset(sigset_t *set) {
*set = 0;
return 0;
}
Note that the <signal.h>
header file also contains a prototype for this function:
int sigemptyset(sigset_t *);
In your code, a call sigemptyset(&sigset)
invokes the macro, but you can force a reference to the library function by writing (sigemptyset)(&sigset)
or by taking a pointer to the function. The macro allows for inline expansion without a change of prototype. clang can perform inline expansion at link time for small functions, but not for functions defined inside dynamic libraries.
The same trick is used for other functions in the header file, for which the , 0)
is necessary for the expression to evaluate to 0
with type int
:
#define sigaddset(set, signo) (*(set) |= __sigbits(signo), 0)
#define sigdelset(set, signo) (*(set) &= ~__sigbits(signo), 0)
#define sigemptyset(set) (*(set) = 0, 0)
#define sigfillset(set) (*(set) = ~(sigset_t)0, 0)
答案2
得分: 1
在这个表达式中
(*(set) = 0, 0)
使用了逗号操作符。
表达式的结果是0。
作为副作用,指针 set
指向的对象被设为了0。
根据C标准(6.5.17 逗号操作符)
2 逗号操作符的左操作数被评估为一个
void
表达式;它的评估和右操作数之间有一个序列点。然后评估右操作数;结果具有它的类型和值。
英文:
In this expression
(*(set) = 0, 0)
there is used the comma operator.
The result of the expression is 0.
As a side effect the object pointed to by the pointer set
is set to 0.
From the C Standard (6.5.17 Comma operator)
> 2 The left operand of a comma operator is evaluated as a void
> expression; there is a sequence point between its evaluation and that
> of the right operand. Then the right operand is evaluated; the result
> has its type and value.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论