2017-10-07 128 views
0

對不起,如果這是一個非常長的代碼,但唯一的問題是LinkedList類中的remove()方法,並且我一直在這個代碼上掙扎幾個小時,似乎無法找到解決方案。每當我輸入地址456的主要方法,而不是打印爲什麼我的自定義LinkedList中的remove()方法無法正常工作?

0+6+5+4 
RESULT 15 

我不斷獲取

0+6+6+4 
RESULT 16 

這意味着要麼刪除()或插入()方法出了問題,但是當我檢查insert()方法的輸入5在必要時被正確插入。所以我想知道remove()方法的哪一部分出錯了,我該如何解決它。謝謝。

這些是接口。

接口堆棧。

package ds.stack; 

public interface Stack<E> { 
/* 
* Removes all of the elements in this stack. 
*/ 
public void clear(); 

/* 
* Pushes an item onto the top of this stack. 
* 
* @param item 
*   the item to be pushed onto this stack 
*/ 
public void push(E item); 

/** 
* Removes the item at the top of this stack and returns that item as the 
* value of this method. 
* 
* @return the item at the top of this stack, or null if this stack is empty 
*/ 
public E pop(); 

/** 
* Returns the number of elements in this stack. 
* 
* @return the number of elements in this stack 
*/ 
public int length(); 

/** 
* Returns true if this stack contains no elements. 
* 
* @return true if this stack contains no elements 
*/ 
public boolean isEmpty(); 
} 

接口列表。

package ds.list; 

public interface List<E> { 
/** 
* Removes all of the elements from this list. 
*/ 
public void clear(); 

/** 
* Inserts the specified element at the specified position in this list. 
* 
* @param pos 
*   index at which the specified element is to be inserted 
* @param item 
*   element to be inserted 
*/ 
public void insert(int pos, E item); 

/** 
* Removes the element at the specified position in this list. Shifts any 
* subsequent elements to the left (subtracts one from their indices). 
* Returns the element that was removed from the list. 
* 
* @param pos 
*   the index of the element to be removed 
* @return the element previously at the specified position 
*/ 
public E remove(int pos); 

/** 
* Returns the number of elements in this list. 
* 
* @return the number of elements in this list. 
*/ 
public int length(); 

/** 
* Returns the element at the specified position in this list. 
* 
* @param pos 
*   index of the element to return 
* @return the element at the specified position in this list 
*/ 
public E getValue(int pos); 
} 

這裏是我的LinkedList類

package ds.list; 

public class LinkedList<E> implements List<E> { 
private E element; 
private LinkedList<E> next; 
private LinkedList<E> head; 
private LinkedList<E> tail; 
private LinkedList<E> curr; 
public int cnt=0; //length of the list 
/* 
* constructors below 
*/ 
public LinkedList() { //The very initial constructor 
    curr = tail = head = this; 
} 
public LinkedList(LinkedList<E> nextval) { //when you start making more bundles 
    next = nextval; 
} 

public void setNext(LinkedList<E> nextval) { 
    next = nextval; 
} 

public void goNext() { 
    curr = next; 
} // curr becomes the next bundle 

public void setValue(E item) { 
    element = item; 
} 
@Override 
public void clear() { 
    tail = head = new LinkedList<E>(); 
    next = null; 
    cnt = 0; 
} 

@Override 
public void insert(int pos, E item) { 
    if(pos<0||pos>cnt+1) { 
     return; 
    } 
    if(pos==0) { 
     curr = head; 
     head = new LinkedList<E>(curr); 
     curr = head; 
     curr.setValue(item); 
    } 
    curr = head; 
    for(int i=0;i<pos-1;i++) { 
     goNext(); 
    } //curr points right before the index of pos 
    LinkedList<E> temp = curr.next; 
    curr.setNext(new LinkedList<E>(temp)); 
    curr.goNext(); 
    curr.setValue(item); 
    cnt++; 
} 

@Override 
public E remove(int pos) { 
    if(pos<0||pos>cnt) 
     return null; 
    curr = head; 
    if(cnt==1) { 
     E it = element; 
     curr = head = tail = null; 
     cnt--; 
     return it; 
    } 
    for(int i=0;i<pos-1;i++) { 
     goNext(); 
    } 
    E it = next.element; 
    curr.setNext(next.next); 
    cnt--; 
    return it; 
} 

@Override 
public int length() { 
    return cnt; 
} 

@Override 
public E getValue(int pos) { 
    if(pos<0||pos>cnt) 
     return null; 
    curr = head; 
    for(int i=0;i<pos-1;i++) { 
     goNext(); 
    } 
    return next.element; 
} 
} 

,這是我LinkedStack類,利用LinkedList類

package ds.stack; 

import ds.list.LinkedList; 

public class LinkedStack<E> implements Stack<E> { 
private LinkedList<E> stack = new LinkedList<E>(); 
@Override 
public void clear() { 
    stack.clear(); 
} 

@Override 
public void push(E item) { 
    if(stack.cnt == 0) { 
     stack.setValue(item); 
     stack.cnt++; 
     return; 
    } 
    stack.insert(stack.length(),item); 
} 

@Override 
public E pop() { 
    if(stack.length()==0) { 
     return null; 
    } 
    else { 
     return stack.remove(stack.length()-1); 
    } 
} 

@Override 
public int length() { 
    return stack.length(); 
} 

@Override 
public boolean isEmpty() { 
    if(stack.length()==0) 
     return true; 
    return false; 
} 

} 

那麼這是一個使用LinkedStack類

我BabyCalculator類
package ds.test; 

import ds.stack.LinkedStack; 
import ds.stack.Stack; 

public class BabyCalculator { 
Stack<Character> stack = new LinkedStack<Character>(); 
private int value=0; 

public int murmurAdd(String polynomial) { 
    char[] charPol=polynomial.toCharArray(); 
    int count=0; 
    for(int i=0;i<polynomial.length();i++) { 
     if(!(Character.isDigit(charPol[i]))) 
      count++; 
    } // This counts the total number of (and)s. 
    int numOf=count/2; 
    if (numOf==0) { 
     for(int i=0;i<polynomial.length();i++) { 
      stack.push(charPol[i]); 
     } 
    } 
    else { 
     for(int i=0;i<numOf;i++) { 
      int num1=0, num2 = 0; //will become the index of last (and first) 
      for(int j=0;j<polynomial.length();j++) { 
       if(charPol[j]=='(') 
        num1 = j; 
       if(charPol[j]==')') { 
        num2 = j; 
        break; 
       } 
      } 
      for(int index=num1+1;index<num2;index++) { 
       stack.push(charPol[index]); 
      } 
      StringBuilder polytemp = new StringBuilder(polynomial); 
      polynomial=polytemp.replace(num1, num2+1, "").toString(); 
     } 
     if(polynomial.length()>0) { 
      charPol = polynomial.toCharArray(); 
      for(int i=0;i<polynomial.length();i++) { 
       stack.push(charPol[i]); 
      } 
     } 
    } 
    System.out.print(value); 
    while(!(stack.isEmpty())) { 
      Character a = stack.pop(); 
      System.out.println(" a is "+a); 
      value += Character.getNumericValue(a); 
      System.out.print("+"+a); 
    } 
    System.out.println(); 
    return value; 
} 

public int getValue() { 
    // TODO Implement this method 
    return value; 
} 

public void setValue(int newValue) { 
    // TODO Implement this method 
    value = newValue; 
} 
} 

最後,使用BabyCalculator的main()方法。

package ds.test; 

import java.util.Scanner; 

public class Main { 

public static void main(String[] args) { 
    BabyCalculator babyCalculator = new BabyCalculator(); 
    Scanner sc = new Scanner(System.in); 

    while (sc.hasNext()) { 
     String command = sc.next(); 
     if ("ADD".equals(command)) { 
      String equation = sc.next(); 
      babyCalculator.murmurAdd(equation); 
      System.out.println("RESULT "+babyCalculator.getValue()); 
      // TODO 
     } else if ("SHOW".equals(command)) { 
      System.out.println("VALUE "+babyCalculator.getValue()); 
      // TODO 
     } else if ("CLEAR".equals(command)) { 
      babyCalculator.setValue(0); 
      System.out.println("VALUE CLEARED"); 
      // TODO 
     } else if ("SET".equals(command)) { 
      int newValue = sc.nextInt(); 
      babyCalculator.setValue(newValue); 
      System.out.println("VALUE SET TO "+babyCalculator.getValue()); 
      // TODO 
     } else if ("EXIT".equals(command)) { 
      System.out.println("FINAL VALUE "+ babyCalculator.getValue()); 
      return; 
      // TODO 
     } 
    } 
    sc.close(); 
} 
} 

編輯:當我試圖ADD(2345),其結果是

0+5+5+5+2 
RESULT 17 

這意味着5保持飛出只有等到它的時間爲2蹦出來。爲什麼這會繼續發生?我假設這是LinkedList類中的一個深層次的指向問題。

+0

堆棧是你的界面?什麼是堆棧導入?我想嘗試你的代碼,但不能編譯... – Optional

+0

哦,我認爲沒有必要的界面。我會導入它謝謝。 –

+0

似乎你正在處理自定義接口。我認爲這是標準的JDK列表..我甚至無法編譯該類。 – Optional

回答

1

那麼,我可以肯定地說你的LinkedList沒有正確實施。在構建基礎類之前,您需要對基礎類進行單元測試。只需插入幾個元素到位置0,然後嘗試獲取位置0,1和2中的項目值的基本測試就會失敗。

這是我寫的基本測試,它與NullPointerException失敗。

LinkedList<String> list = new LinkedList<>(); 
list.insert(0, "A"); 
list.insert(0, "B"); 
list.insert(0, "C"); 

System.out.println(list.getValue(0)); 
System.out.println(list.getValue(1)); 
System.out.println(list.getValue(2)); 

添加更多的日誌記錄在你的代碼,使用調試器,實現在你的類toString方法來幫助您找到問題。

我可以告訴你,你的LinkedList方法getValue不能按預期工作。爲了讓我上面的測試工作,我不得不從:

for(int i=0;i<pos-1;i++) { 
    goNext(); 
} 
return next.element; 

這樣:

for (int i = 0; i < pos; i++) { 
    goNext(); 
} 
return curr.element; 

的原因是因爲「下一個」是指接下來的任何LinkedList的你叫getValue元素,而不是當前之後的下一個元素。

我還可以告訴你,你有類似的bug在你goNext方法LinkedList

public void goNext() { 
    curr = next; 
} 

應該是:

public void goNext() { 
    curr = curr.next; 
} 

幾乎肯定更多與此類問題,所以我強烈建議您徹底測試並進行調試,因爲這可能會解決您的許多問題。

+0

哇謝謝你!這是我第一次編程多個類,所以我不知道何時以及如何測試一個類的有效性。感謝您的提示和解釋。現在我明白何時使用'curr.next'和'下一個'。 –

+0

不客氣。有關進一步閱讀,請參閱[JUnit測試框架](http://junit.org/junit5/)。編寫自動化測試可以爲您節省很多頭痛,因爲您可以進行更改,然後重新運行所有測試,以確保您不會破壞以前工作的任何內容。 –

0

我看到的問題不止一個。插入錯誤,刪除錯誤(您可以驗證)通過在同一次運行中調用ADD兩次。

其中一個問題是插入我爲如下代碼:

//LinkedList<E> temp = curr.next; 
    //curr.setNext(new LinkedList<E>(temp)); 
    LinkedList<E> temp = new LinkedList<E>(curr.next); 
    temp.setValue(curr.element); 

並刪除在remove方法至少應循環

for(int i=0;i<pos-1;i++) { 
    goNext(); 
} 

添加測試工作。但你手頭有更多問題。我沒有測試其他許多用例。

相關問題