life is egg

[C언어] free() 와 NULL 본문

sw정글

[C언어] free() 와 NULL

삶은계란진재혁 2024. 4. 6. 22:07

linked list의 노드를 삭제하는 과정에서 동적 할당 받은 포인터주소값을 해제시키기전에 해제시킬 노드가 다음에 가리킬 포인터를 NULL로 초기화 해줄 필요가 있을까 해서 찾아봤다.

 

아래는 해당 코드다 

이중포인터가 상당히 마음에 안든다.. 바꿔주고싶다

void delete_node(struct Node **head, int index)
{
    int list_len=node_len(*head);
    if((*head)->next== NULL)
    {
        printf("리스트가 비어있스빈다.\n");
        return;
    } 
    else if (index<0 || index>list_len)
    {
        printf("리스트의 범위를 넘어선 접근입니다. 리스트의 길이는 %3d 입니다.\n",list_len);
        return;
    }

    if(index ==0)
    {
        struct Node *temp = *head;
        *head = (*head) -> next;
        free(temp);
        return;
    }

    struct Node *pre=*head;

    int i=0;
    while(i<index-1)
    {
        i++;
        pre = pre->next;
    }

    struct Node *target_node=pre->next;

    if(target_node==NULL)
    {
        printf("삭제할 노드가 존재하지 않습니다.\n");
        return;
    }

    pre->next = target_node->next;
    target_node->next = NULL;
    free(target_node);
    target_node==NULL;
}

 


 

  1. 명확한 의도 표현 : 타겟 노드의 next 포인터를 NULL로 설정함으로써, 해당 노드가 더이상 리스트의 다음부분을 가리키지 않도록 명시적으로 나타냄.
  2. 안전한 메모리 해제 : free 함수를 호출하여 메모리를 해제한 후에는 해당 메모리 영역을 사용할 수 없는데 삭제할 노드의 다음 포인터를 NULL 로 설정함으로써, 실수로 이미 free 된 메모리를 참조하려는 시도를 방지할 수있다.
    1. 이와 관련해. 만약 free 이후에 해당 해당 node 구조체가 할당된 곳의 next 포인터를 참조하게 되면 프로그램은 NULL 포인터를 참조하게되므로  디버깅이 쉽다. 
    2. 이와 관련해 free 시킨 노드도 NULL로 처리해주는게 효과적

 

이와 관련해 free 이후..

 

free 함수를 호출하면 , 해당 메모리 영역은 운영체제나 메모리 관리자에게 반환되어 다시 사용될 수 있게 된다.

하지만 free 된 메모리를 가리키는 포인터는 여전히 그 메모리 영역의 주소를 가지고 있을 수 있기때문에, 안전하게 포인터변수를  NULL 로 초기화 시켜주자.

Comments