如何在结构c中释放双指针?

时间:2018-04-12 14:19:04

标签: c pointers struct free

我试图实现Queue.In我的deleteq函数我想只释放指向另一个struct(elemet of queue)的指针并返回指向已删除元素的值的指针,但是free函数会导致错误:Segmentation fault。

struct Node{
   void* val;
   struct Node* next;
};

typedef struct Queue{
    struct Node* head;
    struct Node* tail;
}Queue;

Queue nw_queue(void* val){
    struct Node *node_ptr = (struct Node*)malloc(sizeof(struct Node));
    node_ptr->val = val;
    node_ptr->next = NULL;
    Queue q;
    q.head = node_ptr;
    q.tail = node_ptr;
    return q;
}



void add(Queue *q, void* val){
    struct Node *node_ptr = (struct Node*)malloc(sizeof(struct Node));
    node_ptr->val = val;
    node_ptr->next = NULL;
    if (empty(*q)){
        *q = nw_queue(val);
        return ;
    }
    q->tail->next = node_ptr;
    q->tail = node_ptr;
}

void* deleteq(Queue* q_ptr){
    if (empty(*q_ptr)){
        puts("Error deleteq:Empty queue");
        return NULL;
    }
    struct Node* cur_head = q_ptr->head;
    q_ptr->head = q_ptr->head->next;
    struct Node** toFree = &(cur_head->next);
    free(toFree); //Error
    return cur_head->val;
}

int main()
{
    int a = 5;
    Queue q = nw_queue(&a);
    add(&q, &a);
    deleteq(&q);
    return 0;
}

2 个答案:

答案 0 :(得分:0)

我不明白你想要达到的目标,但以下肯定是错误的

struct Node** toFree = &(cur_head->next);
free(toFree); //Error

您正在释放堆栈地址,而不是malloc() / calloc() / realloc()返回的指针,您传递给{的其他任何内容{1}}是未定义的行为。

因此修复方法是,只传递给您free()free()malloc(),即动态分配内存的任何内容{。}}。

为什么我确定上面的代码是错误的?知道calloc()将为您提供某些内容的地址,并且该指针当然不是由realloc()&malloc()返回的唯一指针允许calloc()编辑。

答案 1 :(得分:0)

以下提议的代码:

  1. 仅创建单个链接列表而不是双链接列表。由OP来添加'prev'链接
  2. 为方便起见。使用了不同的函数名称
  3. 取消了队列功能的创建
  4. 消除了对与其他队列节点完全不同的队列头的处理
  5. 从C库函数中正确检查错误指示
  6. 为了灵活性,将struct定义与struct
  7. 的typedef分开
  8. 不会创建循环队列
  9. 以下代码应将OP指向正确的方向,而不是为它们编写所有代码。

    #include <stdio.h>
    #include <stdlib.h>
    
    
    struct Queue
    {
        void   *data;
        struct Queue* next;
        struct Queue* prev;
    };
    typedef struct Queue Queue;
    
    
    // prototypes
    void addq( Queue **q, void* val );
    void delq( Queue **q );
    
    
    int main( void )
    {
        int a = 5;
        Queue *q = NULL;
    
        addq( &q, (void*)&a);
        delq( &q);
    
        return 0;
    }
    
    
    void addq( Queue **q, void* val )
    {
        struct Queue *node_ptr = malloc(sizeof(*node_ptr ));
        if( !node_ptr )
        {
            perror( "malloc failed" );
            exit( EXIT_FAILURE );
        }
    
        // implied else, malloc successful
    
        node_ptr->data = val;
        node_ptr->next = NULL;
    
        if (!*q )
        {
            *q = node_ptr;
            return ;
        }
    
        Queue *current;
        for( current = *q; current->next; current = current->next );
    
        current->next = node_ptr;
    }
    
    
    void delq( Queue **q )
    {
        if( !*q )
        {
            puts("Error deleteq:Empty queue");
        }
    
        struct Queue  *cur_head = *q;
        *q = (*q)->next;
    
        free( cur_head );
    }