Tôi đang cố gắng bọc đầu quanh khái niệm sử dụng các macro để xác định các hoạt động cấu trúc dữ liệu. Đoạn mã sau là một ví dụ đơn giản để sử dụng thư viện được xây dựng sẵn trong FreeBSD. Trong thư viện, tất cả các hoạt động được định nghĩa là macro. Tôi đã thấy cách tiếp cận này trong vài thư viện khác.Sử dụng các macro trong C để xác định cấu trúc dữ liệu
Tôi có thể thấy rằng điều này có một số lợi thế, ví dụ: là khả năng sử dụng bất kỳ cấu trúc dữ liệu nào làm phần tử trong danh sách. Nhưng tôi không hoàn toàn hiểu cách làm việc này. Ví dụ:
stailhead
là gì? Điều này có vẻ là "chỉ" được xác định.- Cách vượt qua
head
vàentries
cho một chức năng? - Loại nào là
head
, làm cách nào để khai báo một con trỏ?
Có tên chuẩn cho kỹ thuật này mà tôi có thể sử dụng để tìm kiếm trên google hoặc bất kỳ cuốn sách nào giải thích khái niệm này không? Bất kỳ liên kết hoặc giải thích tốt như thế nào kỹ thuật này hoạt động sẽ được nhiều đánh giá cao.
Nhờ Niklas B. Tôi chạy gcc -E
và có định nghĩa này cho head
struct stailhead {
struct stailq_entry *stqh_first;
struct stailq_entry **stqh_last;
} head = { ((void *)0), &(head).stqh_first };
và điều này cho stailq_entry
struct stailq_entry {
int value;
struct { struct stailq_entry *stqe_next; } entries;
};
Vì vậy, tôi đoán head
là loại struct stailhead
.
#include <stdio.h>
#include <stdlib.h>
#include <sys/queue.h>
struct stailq_entry {
int value;
STAILQ_ENTRY(stailq_entry) entries;
};
int main(void)
{
STAILQ_HEAD(stailhead, stailq_entry) head = STAILQ_HEAD_INITIALIZER(head);
struct stailq_entry *n1;
unsigned i;
STAILQ_INIT(&head); /* Initialize the queue. */
for (i=0;i<10;i++){
n1 = malloc(sizeof(struct stailq_entry)); /* Insert at the head. */
n1->value = i;
STAILQ_INSERT_HEAD(&head, n1, entries);
}
n1 = NULL;
while (!STAILQ_EMPTY(&head)) {
n1 = STAILQ_LAST(&head, stailq_entry, entries);
STAILQ_REMOVE(&head, n1, stailq_entry, entries);
printf ("n2: %d\n", n1->value);
free(n1);
}
return (0);
}
Chuyển đến tiêu đề thích hợp và xem 'STAILQ_HEAD',' STAILQ_INIT' mở rộng thành –
Hoặc chỉ sử dụng 'gcc -E'. BTW, cách này bằng cách sử dụng macro là hữu ích để mô phỏng generics trong C. –
Ở cái nhìn đầu tiên, tôi tin rằng bằng cách sử dụng STAILQ_HEAD_INITIALIZER trong định nghĩa, và sau đó STAILQ_INIT là dư thừa. Tôi tin rằng họ cũng làm như vậy. – abelenky