2013-07-01 2 views
0

단일 값으로 연결된 목록에서 대상 값과 동일한 인스턴스를 모두 제거하는 재귀 적 메서드를 정의하려고합니다. 나는 remove 메소드와 함께 removeAux 메소드를 정의했다. 헤드를 제거해야 할 경우 헤드를 재 할당 할 수 있도록 어떻게 변경할 수 있습니까?연결된 목록 재귀 removeAll 메서드

public class LinkedList<T extends Comparable<T>> { 

private class Node { 
    private T data; 
    private Node next; 

    private Node(T data) { 
     this.data = data; 
     next = null; 
    } 
} 

private Node head; 

public LinkedList() { 
    head = null; 
} 

public void remove(T target) { 
    if (head == null) { 
     return; 
    } 

    while (target.compareTo(head.data) == 0) { 
     head = head.next; 
    } 

    removeAux(target, head, null); 
} 

public void removeAux(T target, Node current, Node previous) { 
    if (target.compareTo(current.data) == 0) { 
     if (previous == null) { 
      head = current.next; 
     } else { 
      previous.next = current.next; 
     } 
     current = current.next; 
     removeAux(target, current, previous); // previous doesn't change 

    } else { 
     removeAux(target, current.next, current); 
    } 
} 
+1

이것은 데이터 구조와 알고리즘의 실제 불일치입니다. 목록은 _linear_이며 목록에 재귀를 사용하는 데 별다른 의미가 없습니다. 그것이 _ 트리 _이면, 재귀가 적절할 것입니다. –

+0

시간이 있다면 제 솔루션을보십시오 –

답변

0

난 당신이 대답 graphically linked list 당신을 도울 수도 있습니다

public void remove(T target){ 
    removeAux(target,head, null); 
} 


public void removeAux(T target, Node current, Node previous) { 
     //case base 
     if(current == null) 
       return; 

    if (target.compareTo(current.data) == 0) { 

     if (previous == null) { 
      // is the head 
      head = current.next; 
     } else { 
      //is not the head 
      previous.next = current.next; 
     } 
     current = current.next; 
     removeAux(target, current, previous); // previous doesn't change 

    } else { 
     removeAux(target, current.next, current); 
    } 
} 

확인과 같은 다음 일에 이전 전환 제거 할 때 이전에 대한 참조를 전달하는 것을 선호 : 여기에 지금까지 무엇을 가지고 그것을 구현하는 방법을 생각해보십시오. 훈련 용으로 좋지만 반복적으로 할 수있는 경우.

+0

도움을 주셔서 감사합니다. 내 메소드를 약간 변경했고 removeAux 메소드에 대한 첫 번째 호출에서 removeAux (target, head, head.next)를 전달 중입니다. 나는이 일을 시도 : public void removeAux (T target, Node previous, Node current) { \t \t if (현재 == null) { \t \t \t return; \t \t한다} else {\t \t \t 경우 (target.compareTo (current.data) == 0) { \t \t \t \t previous.next = current.next; \t \t \t \t current = previous.next; \t \t \t} \t \t \t removeAux (target, previous, current); \t \t} \t}하지만 이제 스택 오버플로 오류가 발생합니다. 어떤 아이디어? – Chip

+0

나는 당신이 게시 한 모든 것을 이해하지 못한다. 그러나 처음 전화 할 때 실제 = head와 previous = null ... 그리고 다음에 비교하지 않는다면 .. – nachokk

+0

@ user2506781과 비교하면 내가 편집하고 일부 코드를 게시한다. , 그것은 내가 테스트를하지 않았 으면 좋겠다. 나는 실수를했을지 모르지만 이것이 이상적인 링크이다. – nachokk

0

이렇게하면 작동하도록 함수를 멋지게 만들 수 있습니다.

head = removeAux(target, head); // returns new head 

Coursera 's Algorithms 클래스에서 알 수없는 멋진 트릭.

나머지 코드는 다음과 같습니다.

public void removeAux(T target, Node current) { 
    //case base 
    if(current == null) 
      return null; 

    current.next = removeAux(target, current.next); 

    return target.compareTo(current.data) == 0? current.next: current; // the actual deleting happens here 
}