2011-03-12 8 views
1

다음 루틴은 단일 링크 목록 시작시 노드를 제거 할 것으로 예상되지만 때때로 실패합니다.때때로 프로그램이 충돌 함

void remove_from_front(node *start) 
{ 
    delete start; 
    start = start->link; 
    print_list(start); 
} 

답변

7

나는 볼 수

  1. 을 당신은 해제 된 메모리에 접근 한 후 start 노드를 확보하고있다. 이것은 잘못된 것이며, 정의되지 않은 동작으로 이어 지므로 어떤 일이 발생할 수 있습니다. 하나의 실행에서는 작동 할 수도 있고 다음 실행에서는 충돌 할 수도 있습니다.

  2. 함수가 목록의 머리글을 변경해야하지만 변경된 내용을 반환하지 않으며 인수 start이 전달됩니다. 이 문제를 해결하려면 start 포인터의 주소 또는 참조를 전달하십시오.

  3. 빈 목록에 함수가 호출 될 수 있습니다 (start = NULL). 그 사건을 처리해야합니다.

올바른 구현 :

void remove_from_front(node **start) { 

    // if list is empty..nothing to remove..return. 
    if(*start == NULL) { 
    return; 
    } 

    // save the address of the node following the start in new_start 
    node *new_start = (*start)->link; 

    // now delete the start node. 
    delete *start; 

// new_start is now the new start of the list. 
// And since start was passed by address, the change is reflected in the 
// calling function. 
    *start = new_start; 
} 
+0

이것은 완전한 대답입니다. +1 – Muggen

+0

+1 좋은 설명 – GWW

+0

항상 코드를 읽기 쉽게하기 위해'node * temp = * start'를 할 수 있습니다. – Muggen

-1

시작을 삭제 한 다음 링크 멤버를 가져 와서 참조를 취소하려고합니다. 방금 삭제했기 때문에 충돌이 발생합니다.

node *temp = start; 
start = start->link; 
delete temp; 
print_list(start); 
+0

링크 부재를 얻을 수있는 역 참조는 아주 아주 가능성이 충돌하는 것입니다. 인쇄가 더 그렇습니다. –

5

당신 delete start 후에는 안전하게 start가 가리키는 데 사용 어떤 조각을 사용할 수 없습니다 : 당신은 아마 이런 식으로 뭔가를 할 수 있습니다. 그것은 연 끈을 놓아두고 나중에 다시 잡을 수 있기를 기대하는 것과 같습니다. 효과가있을 수 있습니다. 그렇지 않을 수도 있습니다. 몇 가지 문제가 있습니다

관련 문제