我的程序抛出异常,试图从链接列表中删除元素

时间:2019-05-02 02:12:46

标签: c linked-list dynamic-memory-allocation

我有一个链接列表和两个功能-一个要添加,另一个要从列表中删除成员。 当我尝试删除成员时,删除功能出现异常。

例外在行

if (strcmp((temp_person_ptr->name), name_to_remove))

异常说-> singly_linked_list.exe中0x50C4EF18(ucrtbased.dll)的未处理异常:0xC0000005:访问冲突读取位置0xDDDDDDDD。发生

完整程序在下面-


#include <stdio.h>
#include <conio.h>
#include <stdlib.h>
#include <string.h>
#include "globals.h"

extern struct person* starting_address;

struct person* delete_person(size_t* list_size_ptr, struct person* ptr_current_person)
{
    printf("There are %u items in list \n", *list_size_ptr);

    struct person* temp_person_ptr = starting_address, *to_save_person_ptr;
    printf("The items in list are \n");
    while (temp_person_ptr)
    {
        printf("%s \n", temp_person_ptr->name);
        temp_person_ptr = temp_person_ptr->next_person_ptr;
    }

    char name_to_remove[MAX_NAME_LENGTH];
    printf("Please enter the name to remove \n");
    gets_s(name_to_remove, MAX_NAME_LENGTH - 1);

    temp_person_ptr = starting_address;
    to_save_person_ptr = starting_address; // Not required by logic - just to initialize for compiler
    while (temp_person_ptr)
    {
        if (strcmp((temp_person_ptr->name), name_to_remove))
        {
            to_save_person_ptr = temp_person_ptr;
            temp_person_ptr = temp_person_ptr->next_person_ptr;
        }
        else
        {
            // Since we are going to remove temp_person_ptr - we save it's next person_ptr in preceding person which is to_save_person_ptr
            // Only if the person_ptr to be removed is NOT the first person
            // For now - assume - one element name will match
            if (temp_person_ptr != starting_address)
                to_save_person_ptr->next_person_ptr = temp_person_ptr->next_person_ptr; // takes care if temp_person_ptr is the last one as well
            else // Else the next person's address is the new starting address
                starting_address = temp_person_ptr->next_person_ptr;

            free(temp_person_ptr);
            (*list_size_ptr)--;
        }
    }
    return (ptr_current_person);
}

将元素添加到列表的部分如下所示(整个功能)-

struct person* add_person(size_t* list_size_ptr, struct person* ptr_current_person)
{

    struct person *ptr_new_person;

    ptr_new_person = (struct person*) malloc(sizeof(struct person));

    // If first person- its starting address is the starting address of list
    if ((*list_size_ptr) == 0)
    {
        starting_address = ptr_new_person;
    }
    else
    {
        //1. Add the new address to the chain - only if this is not the first person
        ptr_current_person->next_person_ptr = ptr_new_person;
    }
    ptr_new_person->next_person_ptr = NULL;

    printf("Please enter the name \n");
    gets_s(ptr_new_person->name, MAX_NAME_LENGTH - 1);

    // 2. We may make ptr_new_person as ptr_current_person
    ptr_current_person = ptr_new_person;
    // 3. Now onwards ptr_current_person refers to the pointer to the newly added person

    (*list_size_ptr)++;
    return (ptr_current_person);
}

3 个答案:

答案 0 :(得分:1)

while (temp_person_ptr)
{
    if (strcmp((temp_person_ptr->name), name_to_remove))
    {
        to_save_person_ptr = temp_person_ptr;
        temp_person_ptr = temp_person_ptr->next_person_ptr;
    }
    else{...}

在此代码段中,看起来temp_person_ptr指向某物,但-> name为NULL。在strcmp之前添加这样的printf语句:

if(!(temp_person_ptr->name)){
      printf("This is why your segfaulting\n");
    }

您将看到-> name为null或其他名称。祝你好运

答案 1 :(得分:1)

您发布的信息不足,无法获得适当的分析和帮助。给出完整的最小示例的指导不仅针对咧嘴笑;通常,通过将问题减少到其核心,程序员可以自己发现错误。如果没有的话,它为其他提供了很大的空间。无论如何,删除中的循环本质上是:

temp = start;
while (temp) {
    if (strcmp(temp->name, name)) {
         temp = temp->next;
    } else {
         free(temp);
    }
}

您的自由时间应该像这样:

void *p = temp->next;
free(temp);
temp = p;

答案 2 :(得分:0)

工作正常,我没有在空闲后退出while循环并一直执行。 我添加了返回,返回完成后返回,列表大小递减。现在可以使用了。