在 Java 中出队
Dequeues in Java
我在完全实现入队和出队部分时遇到了问题。这是我想要得到的结果:
DEQUE TESTING
The size of the deque is: 3
The deque contains:
4 9 8
4
8
9
1
11
The size of the deque is: 2
The deque contains:
11 1
但这就是我得到的:
DEQUE TESTING
The size of the deque is: 3
The deque contains:
4 9 8
4
null
null
null
null
The size of the deque is: 0
The deque contains:
所以,它只打印到某个点。我已经多次检查我的代码(实际上很多次)以试图纠正这个问题,但我无法确定问题出在哪里。我有一种感觉,这是一些需要改变的小事。
这是我的代码:
public class Murray_A06Q3 {
public static void main(String[] args) {
LinkedDeque<Integer> deque = new LinkedDeque<Integer>();
System.out.println("DEQUE TESTING");
deque.enqueueBack(3);
deque.enqueueBack(7);
deque.enqueueBack(4);
deque.dequeueFront();
deque.enqueueBack(9);
deque.enqueueBack(8);
deque.dequeueFront();
System.out.println("The size of the deque is: " + deque.size());
System.out.println("The deque contains:\n" + deque.toString());
System.out.println(deque.dequeueFront());
deque.enqueueFront(1);
deque.enqueueFront(11);
deque.enqueueFront(3);
deque.enqueueFront(5);
System.out.println(deque.dequeueBack());
System.out.println(deque.dequeueBack());
System.out.println(deque.last());
deque.dequeueFront();
deque.dequeueFront();
System.out.println(deque.first());
System.out.println("The size of the deque is: " + deque.size());
System.out.println("The deque contains:\n" + deque.toString());
} // End of main method
public static class LinkedDeque<T> implements DequeADT<T> {
private int count;
private LinearDoubleNode<T> firstNode, lastNode;
// constructor
public LinkedDeque(){
count = 0;
firstNode = null;
lastNode = null;
} // end of constructor
// Beginning of enqueueFront
public void enqueueFront(T element) {
LinearDoubleNode newNode = new LinearDoubleNode();
if(isEmpty()){
lastNode = newNode;
count++;
}
else
firstNode.setPrev(newNode);
firstNode = newNode;
count--;
} // end of enqueFront
// Beginning of enqueueBack
public void enqueueBack(T element) {
LinearDoubleNode<T> node = new LinearDoubleNode<T>(element);
if (isEmpty())
firstNode = node;
else
lastNode.setNext(node);
lastNode = node;
count++;
} // end of enqueueBack
// Beginning of dequeueFront
public T dequeueFront() {
T front = null;
if (!isEmpty()) {
front = firstNode.getElement();
firstNode = firstNode.getNext();
count--;
if (firstNode == null) {
lastNode = null;
}
else
firstNode.setPrev(firstNode);
}
return front;
} // end of dequeueFront
// Beginning of dequeueBack
public T dequeueBack() {
T back = null;
if (!isEmpty()) {
back = lastNode.getElement();
lastNode = lastNode.getPrev();
if (lastNode == null) {
firstNode = null;
}
else
lastNode.setNext(null);
}
return back;
} // end of dequeueBack()
public T first() {
return firstNode.getElement();
}
public T last() {
return lastNode.getElement();
}
// Beginning of isEmpty()
public boolean isEmpty() {
if (count == 0) {
return true;
}
else
return false;
} // End of isEmpty()
// Beginning of size()
public int size() {
return count;
}
// Begin of toString() method
public String toString() {
if (isEmpty()) {
return " ";
}
StringBuilder sb = new StringBuilder();
LinearDoubleNode<T> next = firstNode;
while(next != null){
sb.append(" ").append(next.getElement());
next = next.getNext();
}
return sb.toString();
} // End of toString()
} // End of LinkedDeque
} // End of class header
双linked 列表的第一条规则是当你添加一个元素时你必须维护两个 links。这是您的代码:
public void enqueueFront(T element) {
LinearDoubleNode newNode = new LinearDoubleNode();
if(isEmpty()){
lastNode = newNode;
count++;
}
else
firstNode.setPrev(newNode);
firstNode = newNode;
count--;
} // end of enqueFront
首先,您永远不会将元素的值放入新节点。
其次,队列应该是这样的
A ⇆ B ⇆ C
但让我们看看当队列中只有 "B" 时如何添加 "A"。您的 firstNode
是 "B",您将其 prev
设置为 setPrev
以指向您的 "A".
A ← B
但是你没有link从新的"A"回到"B"。这意味着当你需要从正面看队列时,它似乎只有一个元素——A 没有 "next"!
您的 else
子句应该是:
else {
firstNode.setPrev(newNode);
newNode.setNext(firstNode);
}
然后你就可以从两边遍历列表了。同样的逻辑也应该应用于您的 enqueueBack
。
现在,您的出队逻辑:
public T dequeueFront() {
T front = null;
if (!isEmpty()) {
front = firstNode.getElement();
firstNode = firstNode.getNext();
count--;
if (firstNode == null) {
lastNode = null;
}
else
firstNode.setPrev(firstNode);
}
return front;
}
现在,出队后,将新的 firstNode 的 设置为它自己。这意味着您可能有一个无限循环。执行此操作一次后,如果您尝试通过从后面出队来遍历 "prev" link,您将一次又一次地获得相同的节点。 backlink 应该设置为 null
(顺便说一下,你在 dequeueBack
中正确设置)。
您忘记设置上一个和元素。在增加计数时你也有一些错误。并对一些未抛出的异常保持谨慎。尽管如此,现在应该很简单了。您有以下具有所需输出的工作代码:
public static class LinkedDeque<T> {
private int count;
private LinearDoubleNode<T> firstNode, lastNode;
// constructor
public LinkedDeque(){
count = 0;
firstNode = null;
lastNode = null;
} // end of constructor
// Beginning of enqueueFront
public void enqueueFront(T element) {
LinearDoubleNode newNode = new LinearDoubleNode();
newNode.setElement(element);
if(isEmpty()){
lastNode = newNode;
firstNode = newNode;
}
else {
LinearDoubleNode second=firstNode;
firstNode=newNode;
firstNode.setNext(second);
second.setPrev(firstNode);
// firstNode.setPrev(newNode);
}
count++;
} // end of enqueFront
// Beginning of enqueueBack
public void enqueueBack(T element) {
if (element==null) throw new NullPointerException("cannot add null to the list");
LinearDoubleNode<T> node = new LinearDoubleNode<T>(element);
node.setElement(element);
if (isEmpty()){
firstNode = node;
lastNode=node;}
else{
LinearDoubleNode<T> before=lastNode;
lastNode=node;
before.setNext(lastNode);
lastNode.setPrev(before);
}
count++;
} // end of enqueueBack
// Beginning of dequeueFront
public T dequeueFront() {
T front = null;
if (count==1){
front=firstNode.getElement();
firstNode=null;
lastNode=null;
count--;
}
else if (!isEmpty()) {
count--;
front = firstNode.getElement();
firstNode = firstNode.getNext();
}
return front;
} // end of dequeueFront
// Beginning of dequeueBack
public T dequeueBack() {
T back = null;
if (count==1){
back = lastNode.getElement();
lastNode = null;
firstNode = null;
count--;
}
else if (!isEmpty()) {
count--;
back = lastNode.getElement();
lastNode = lastNode.getPrev();
lastNode.setNext(null);
}
return back;
} // end of dequeueBack()
public T first() {
return firstNode.getElement();
}
public T last() {
return lastNode.getElement();
}
// Beginning of isEmpty()
public boolean isEmpty() {
return count==0;
} // End of isEmpty()
// Beginning of size()
public int size() {
return count;
}
// Begin of toString() method
public String toString() {
if (isEmpty()) {
return " ";
}
StringBuilder sb = new StringBuilder();
LinearDoubleNode<T> next = firstNode;
while(next != null){
sb.append(" ").append(next.getElement());
next = next.getNext();
}
return sb.toString();
} // End of toString()
} // End of LinkedDeque
} // End of class header
DEQUE TESTING
The size of the deque is: 3
The deque contains:
4 9 8
4
8
9
1
11
The size of the deque is: 2
The deque contains:
11 1
我在完全实现入队和出队部分时遇到了问题。这是我想要得到的结果:
DEQUE TESTING
The size of the deque is: 3
The deque contains:
4 9 8
4
8
9
1
11
The size of the deque is: 2
The deque contains:
11 1
但这就是我得到的:
DEQUE TESTING
The size of the deque is: 3
The deque contains:
4 9 8
4
null
null
null
null
The size of the deque is: 0
The deque contains:
所以,它只打印到某个点。我已经多次检查我的代码(实际上很多次)以试图纠正这个问题,但我无法确定问题出在哪里。我有一种感觉,这是一些需要改变的小事。
这是我的代码:
public class Murray_A06Q3 {
public static void main(String[] args) {
LinkedDeque<Integer> deque = new LinkedDeque<Integer>();
System.out.println("DEQUE TESTING");
deque.enqueueBack(3);
deque.enqueueBack(7);
deque.enqueueBack(4);
deque.dequeueFront();
deque.enqueueBack(9);
deque.enqueueBack(8);
deque.dequeueFront();
System.out.println("The size of the deque is: " + deque.size());
System.out.println("The deque contains:\n" + deque.toString());
System.out.println(deque.dequeueFront());
deque.enqueueFront(1);
deque.enqueueFront(11);
deque.enqueueFront(3);
deque.enqueueFront(5);
System.out.println(deque.dequeueBack());
System.out.println(deque.dequeueBack());
System.out.println(deque.last());
deque.dequeueFront();
deque.dequeueFront();
System.out.println(deque.first());
System.out.println("The size of the deque is: " + deque.size());
System.out.println("The deque contains:\n" + deque.toString());
} // End of main method
public static class LinkedDeque<T> implements DequeADT<T> {
private int count;
private LinearDoubleNode<T> firstNode, lastNode;
// constructor
public LinkedDeque(){
count = 0;
firstNode = null;
lastNode = null;
} // end of constructor
// Beginning of enqueueFront
public void enqueueFront(T element) {
LinearDoubleNode newNode = new LinearDoubleNode();
if(isEmpty()){
lastNode = newNode;
count++;
}
else
firstNode.setPrev(newNode);
firstNode = newNode;
count--;
} // end of enqueFront
// Beginning of enqueueBack
public void enqueueBack(T element) {
LinearDoubleNode<T> node = new LinearDoubleNode<T>(element);
if (isEmpty())
firstNode = node;
else
lastNode.setNext(node);
lastNode = node;
count++;
} // end of enqueueBack
// Beginning of dequeueFront
public T dequeueFront() {
T front = null;
if (!isEmpty()) {
front = firstNode.getElement();
firstNode = firstNode.getNext();
count--;
if (firstNode == null) {
lastNode = null;
}
else
firstNode.setPrev(firstNode);
}
return front;
} // end of dequeueFront
// Beginning of dequeueBack
public T dequeueBack() {
T back = null;
if (!isEmpty()) {
back = lastNode.getElement();
lastNode = lastNode.getPrev();
if (lastNode == null) {
firstNode = null;
}
else
lastNode.setNext(null);
}
return back;
} // end of dequeueBack()
public T first() {
return firstNode.getElement();
}
public T last() {
return lastNode.getElement();
}
// Beginning of isEmpty()
public boolean isEmpty() {
if (count == 0) {
return true;
}
else
return false;
} // End of isEmpty()
// Beginning of size()
public int size() {
return count;
}
// Begin of toString() method
public String toString() {
if (isEmpty()) {
return " ";
}
StringBuilder sb = new StringBuilder();
LinearDoubleNode<T> next = firstNode;
while(next != null){
sb.append(" ").append(next.getElement());
next = next.getNext();
}
return sb.toString();
} // End of toString()
} // End of LinkedDeque
} // End of class header
双linked 列表的第一条规则是当你添加一个元素时你必须维护两个 links。这是您的代码:
public void enqueueFront(T element) {
LinearDoubleNode newNode = new LinearDoubleNode();
if(isEmpty()){
lastNode = newNode;
count++;
}
else
firstNode.setPrev(newNode);
firstNode = newNode;
count--;
} // end of enqueFront
首先,您永远不会将元素的值放入新节点。
其次,队列应该是这样的
A ⇆ B ⇆ C
但让我们看看当队列中只有 "B" 时如何添加 "A"。您的 firstNode
是 "B",您将其 prev
设置为 setPrev
以指向您的 "A".
A ← B
但是你没有link从新的"A"回到"B"。这意味着当你需要从正面看队列时,它似乎只有一个元素——A 没有 "next"!
您的 else
子句应该是:
else {
firstNode.setPrev(newNode);
newNode.setNext(firstNode);
}
然后你就可以从两边遍历列表了。同样的逻辑也应该应用于您的 enqueueBack
。
现在,您的出队逻辑:
public T dequeueFront() {
T front = null;
if (!isEmpty()) {
front = firstNode.getElement();
firstNode = firstNode.getNext();
count--;
if (firstNode == null) {
lastNode = null;
}
else
firstNode.setPrev(firstNode);
}
return front;
}
现在,出队后,将新的 firstNode 的 设置为它自己。这意味着您可能有一个无限循环。执行此操作一次后,如果您尝试通过从后面出队来遍历 "prev" link,您将一次又一次地获得相同的节点。 backlink 应该设置为 null
(顺便说一下,你在 dequeueBack
中正确设置)。
您忘记设置上一个和元素。在增加计数时你也有一些错误。并对一些未抛出的异常保持谨慎。尽管如此,现在应该很简单了。您有以下具有所需输出的工作代码:
public static class LinkedDeque<T> {
private int count;
private LinearDoubleNode<T> firstNode, lastNode;
// constructor
public LinkedDeque(){
count = 0;
firstNode = null;
lastNode = null;
} // end of constructor
// Beginning of enqueueFront
public void enqueueFront(T element) {
LinearDoubleNode newNode = new LinearDoubleNode();
newNode.setElement(element);
if(isEmpty()){
lastNode = newNode;
firstNode = newNode;
}
else {
LinearDoubleNode second=firstNode;
firstNode=newNode;
firstNode.setNext(second);
second.setPrev(firstNode);
// firstNode.setPrev(newNode);
}
count++;
} // end of enqueFront
// Beginning of enqueueBack
public void enqueueBack(T element) {
if (element==null) throw new NullPointerException("cannot add null to the list");
LinearDoubleNode<T> node = new LinearDoubleNode<T>(element);
node.setElement(element);
if (isEmpty()){
firstNode = node;
lastNode=node;}
else{
LinearDoubleNode<T> before=lastNode;
lastNode=node;
before.setNext(lastNode);
lastNode.setPrev(before);
}
count++;
} // end of enqueueBack
// Beginning of dequeueFront
public T dequeueFront() {
T front = null;
if (count==1){
front=firstNode.getElement();
firstNode=null;
lastNode=null;
count--;
}
else if (!isEmpty()) {
count--;
front = firstNode.getElement();
firstNode = firstNode.getNext();
}
return front;
} // end of dequeueFront
// Beginning of dequeueBack
public T dequeueBack() {
T back = null;
if (count==1){
back = lastNode.getElement();
lastNode = null;
firstNode = null;
count--;
}
else if (!isEmpty()) {
count--;
back = lastNode.getElement();
lastNode = lastNode.getPrev();
lastNode.setNext(null);
}
return back;
} // end of dequeueBack()
public T first() {
return firstNode.getElement();
}
public T last() {
return lastNode.getElement();
}
// Beginning of isEmpty()
public boolean isEmpty() {
return count==0;
} // End of isEmpty()
// Beginning of size()
public int size() {
return count;
}
// Begin of toString() method
public String toString() {
if (isEmpty()) {
return " ";
}
StringBuilder sb = new StringBuilder();
LinearDoubleNode<T> next = firstNode;
while(next != null){
sb.append(" ").append(next.getElement());
next = next.getNext();
}
return sb.toString();
} // End of toString()
} // End of LinkedDeque
} // End of class header
DEQUE TESTING
The size of the deque is: 3
The deque contains:
4 9 8
4
8
9
1
11
The size of the deque is: 2
The deque contains:
11 1