Стирание элементов из общего (void *) списка в C - PullRequest
1 голос
/ 18 мая 2019

Я пишу общий двусвязный список на C.

typedef struct ListNode {
    void *data;
    struct ListNode *prev;
    struct ListNode *next;
} ListNode;

typedef struct List {
    struct ListNode *head;
    struct ListNode *tail;
} List;

Вставка элемента в список выполняется просто

listNode->data = data;

где listNode - это некоторый элемент списка, а данные - это данные для вставки. Так что я делаю мелкую копию. Теперь, когда я хочу удалить что-то из списка, я хочу иметь возможность выполнить глубокое копирование, поэтому у меня есть функция, выполняющая глубокое удаление объектов, которые я передаю в список. Я хотел бы передать указатель на эту функцию в качестве параметра функции удаления члена списка. Пример приведен ниже.

typedef struct Object {
    int *ptr;
} Object;

void removeObject(Object *object) {
    free(object->ptr);
    free(object);
}

void removeListNodeFromList(List *list, ListNode *listNode,
                               void (*removeEntry)(void *data)) {
    // Code handling removing listNode from list
    // ...

    removeEntry(listNode->data);
    free(listNode);
}

void fun() {
    List *list = NULL;
    ListNode *listNode = NULL;
    // Some code giving specific value to list and listNode
    // ...

    removeListNodeFromList(list, listNode, removeObject);
}

Этот код не будет компилироваться, потому что (последняя строка кода) removeObject несовместимо с removeEntry. Как я могу преодолеть эту проблему?

1 Ответ

3 голосов
/ 18 мая 2019

Для совместимости сигнатур функций ваш removeObject должен принять общий указатель и привести его соответствующим образом:

void removeObject(void *vptr) {
    Object *object = (Object *)vptr;
    free(object->ptr);
    free(object);
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...