【发布时间】:2018-08-11 14:39:36
【问题描述】:
我正在使用一个跟踪最后一个元素的链表在 c 中编写一个简单的队列。
这是我的代码:
#include <stdlib.h>
#include <stdio.h>
#include <stdbool.h>
#include <stdint.h>
typedef struct node_s {
uint32_t x, y;
} node;
// very cheap linked list queue that lives as long as its scope
typedef struct queue_s {
node* node;
struct queue_s* next;
} queue;
bool isEmpty(queue** queue)
{
return !*queue;
}
node* dequeue(queue** head, queue** tail)
{
if (isEmpty(head)) {
printf("attempting to dequeue from an empty queue\n");
return NULL;
}
node* ret = (**head).node;
*head = (*head)->next;
if (isEmpty(head)) *tail = NULL;
printf("next %p\n", (void*) *head);
// no need to free anything, the queue lives as long as its scope
return ret;
}
void enqueue(queue** head, queue** tail, queue* new)
{
if (isEmpty(head)) {
// has no head -> make new head
*head = new;
*tail = new;
printf("empty\n");
} else {
// has head -> make new tail // TODO does this work?
(*tail)->next = new;
*tail = (*tail)->next;
printf("not empty\n");
}
}
int main()
{
queue* head = NULL;
queue* tail = NULL;
enqueue(&head, &tail, &(queue) {.node=&(node) {1, 1}, NULL});
printf("h %i\n", head->node->x);
printf("t %i\n", tail->node->x);
enqueue(&head, &tail, &(queue) {.node=&(node) {2, 2}, NULL});
printf("h %i\n", head->node->x);
printf("t %i\n", tail->node->x);
enqueue(&head, &tail, &(queue) {.node=&(node) {3, 3}, NULL});
printf("h %i\n", head->node->x);
printf("t %i\n", tail->node->x);
// for (int i = 1; i <= 3; ++i) {
// enqueue(&head, &tail, &(queue) {.node=&(node) {i, i}, NULL});
// printf("h %i\n", head->node->x);
// printf("t %i\n", tail->node->x);
// }
return 0;
}
现在 main() 中推出的 for 循环的行为正确,因为头元素保持 1 而新元素排队:
empty
h 1
t 1
not empty
h 1
t 2
not empty
h 1
t 3
...但是 for 循环本身给出了错误的输出,因为头元素总是等于尾元素:
empty
h 1
t 1
not empty
h 2
t 2
not empty
h 3
t 3
我是一个 c 初学者,这让我发疯,有人可以帮帮我吗?
【问题讨论】:
-
&(queue) {.node=&(node) {i, i}, NULL}创建一个局部变量,该变量在封闭块的末尾不再存在。 -
您可能想了解复合文字的生命周期。
标签: c loops for-loop side-effects loop-unrolling