在LIST_FOREACH()宏中添加的_node变量是否仅用于代码可读性?
在一个宏中,我注意到有一个变量在LIST_FOREACH()宏中添加的_node变量是否仅用于代码可读性?,c,macros,readability,function-definition,C,Macros,Readability,Function Definition,在一个宏中,我注意到有一个变量\u node,它似乎是多余的,因为它可以被删除并完全替换为V 它唯一单独使用的时间是在for循环的测试表达式中 \u节点甚至有一个下划线前缀,这意味着它是一个仅供内部使用的变量 此宏中是否存在\u节点,以便于人们阅读 宏 示例用法 void List_destroy(List * list) { LIST_FOREACH(list, first, next, cur) { if (cur->prev){ f
\u node
,它似乎是多余的,因为它可以被删除并完全替换为V
它唯一单独使用的时间是在for循环的测试表达式中
\u节点
甚至有一个下划线前缀,这意味着它是一个仅供内部使用的变量
此宏中是否存在\u节点
,以便于人们阅读
宏
示例用法
void List_destroy(List * list)
{
LIST_FOREACH(list, first, next, cur) {
if (cur->prev){
free(cur->prev);
}
}
free(list->last);
free(list);
}
创建Typedefs
typedef struct ListNode {
struct ListNode *next;
struct ListNode *prev;
void *value;
} ListNode;
typedef struct List {
int count;
ListNode *first;
ListNode *last;
} List;
我认为\u节点
变量的作用是使循环体可以自由修改V
,而不影响迭代。我不会这样写的;我会用
#define LIST_FOREACH(L, S, M, V) \
for(ListNode *V = (L)->S; V; V = V->M)
因为我认为不使用变量声明污染外部范围,以及允许嵌套
LIST\u FOREACH
,更为重要。但是我可以看到单独的V
和\u节点的参数,宏使代码无法读取。这是一种非常糟糕的编程风格
如果要替换此函数中的宏
void List_destroy(List * list)
{
LIST_FOREACH(list, first, next, cur) {
if (cur->prev){
free(cur->prev);
}
}
free(list->last);
free(list);
}
对于它的扩展,您将获得
void List_destroy(List * list)
{
ListNode *_node = NULL;
ListNode *cur = NULL
for( cur = _node = list->first; _node != NULL; cur = _node = _node->next )
{
if (cur->prev){
free(cur->prev);
}
}
free(list->last);
free(list);
}
可以立即看到变量cur
和\u node
应该在使用它们的for循环中声明。此外,变量\u节点
只是冗余的
该函数可以按以下方式重写
void List_destroy(List * list)
{
for( ListNode *cur = list->first; cur != NULL; cur = cur->next )
{
free( cur->prev );
}
free( list->last );
free( list );
}
但是,像这样定义函数更简单、更正确
void List_destroy( List *list )
{
while ( list->first != NULL )
{
ListNode *tmp = list->first;
list->first = lits->first->next;
free( tmp );
}
list->last = NULL;
list->count = 0;
}
该函数不应释放指向列表本身。例如,用户可以定义如下列表
List list = { .count = 0, .first = NULL, .last = NULL };
也就是说,不必动态分配struct List
类型的对象
此外,还完全不清楚数据成员值是否指向动态分配的对象,以及为什么不释放该对象
因此,一般来说,函数应该如下所示
void List_destroy( List *list )
{
while ( list->first != NULL )
{
ListNode *tmp = list->first;
list->first = lits->first->next;
free( tmp->value );
free( tmp );
}
list->last = NULL;
list->count = 0;
}
因此,在我看来,您发现了一个非常糟糕的代码,不值得讨论。:/p>宏使代码无法读取。:)我相信\u node
是此范围内的保留标识符,同样。固定名称\u node
使得无法在同一块中使用此宏两次,因为\u node
将被重新定义。删除\u节点
变量允许在同一块中使用宏两次,但不能使用相同的V
参数,因为相应的变量将被重新定义。更改宏以定义for
循环范围内的变量可以修复这些问题。
void List_destroy( List *list )
{
while ( list->first != NULL )
{
ListNode *tmp = list->first;
list->first = lits->first->next;
free( tmp->value );
free( tmp );
}
list->last = NULL;
list->count = 0;
}