Я реализовал Deque в java с использованием двусвязного списка и при вызове итератора. затем я получаю исключение нулевого указателя

#java #iterator #deque #doubly-linked-list

#java #итератор #deque #двусвязный список

Вопрос:

Когда я запускаю main(), который я предоставил здесь, я всегда получаю эту ошибку.

 java.lang.NullPointerException
    at Deque$Node.access$100(Deque.java:98)
    at Deque$DequeIterator.hasNext(Deque.java:83)
    at Deque.main(Deque.java:116)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:622)
    at edu.rice.cs.drjava.model.compiler.JavacCompiler.runCommand(JavacCompiler.java:272)
 

Почему итератор ничего не возвращает даже для hasNext() ? Я могу использовать панель взаимодействий в drjava, и я могу получить указатель для итератора, но если я попытаюсь использовать какие-либо связанные с ним функции, я получу NullPointerExceptions

 import java.util.Iterator;



public class Deque<Item> implements Iterable<Item> {
 private int size;// number of elements
 private Node before;//sentinel marking the beginning of a list
 private Node after;//sentinel marking the end of a list



    public Deque()                           // construct an empty deque
    {
     before= new Node();
     after = new Node();
     before.next=after;
     after.previous=before;
    }

    public boolean isEmpty()                 // is the deque empty?
    {
     return size>0;
    }

    public int size()                        // return the number of items on the deque
    {
     return size;
    }

    public void addFirst(Item item)          // insert the item at the front
    {
     size  ;
     Node node = new Node();
     node.item=item;//sets new node equal to the item
     node.previous=before;//sets new node's previous to before which is the beginning sentinel
     node.next=before.next;//sets new node's next to the old first node which was befores next.
     before.next.previous=node;//sets old first item's previous to the new Node making the old first second in the list.
     before.next=node;//sets before's next to the new Node making the new Node first in the list.

    }
    public void addLast(Item item)           // insert the item at the end
    {
     size  ;
     Node node = new Node();
     node.item=item;//sets node item to item
     node.next=after;//sets new node's next to after 
     after.previous.next=node;//sets old last node's next to the new node 
     node.previous=after.previous;//sets new node's previous to old last node
     after.previous=node;//now after's previous is the new node making it last in the list.


    }
    public Item removeFirst()                // delete and return the item at the front
    {
     size--;
     Node first= before.next;//gets the first node.
     Node second=first.next;//gets the second element in the list
     second.previous=before;//sets second's previous to before
     before.next=second;//sets before's next to second
     return first.item;


    }

    public Item removeLast()                 // delete and return the item at the end
    {
     size--;
     Node last = after.previous;//sets last node
     Node second2Last= after.previous.previous;//sets second2Last
     second2Last.next=after;//sets second2Last's next to after
     after.previous=second2Last;//sets after's previous to second2last
     return last.item;
    }

    public Iterator<Item> iterator()         // return an iterator over items in order from front to end
    {
     return new DequeIterator();
    }

    private class DequeIterator implements Iterator<Item>{
     Node current=after.next;
     public boolean hasNext(){
      return current.next!=after;

     }
     public void remove(){

     }

     public Item next(){
      Item item=current.item;
      current=current.next;
      return item;   
     }

    }//end class DequeIterator

    private class Node{
     private Item item;
     private Node next;
     private Node previous;

    }

 /**
  * @param args
  */
 public static void main(String[] args) {
  // TODO Auto-generated method stub
  Deque d = new Deque();

  d.addFirst(1);
  d.addLast(2);
  d.addFirst(3);
  Iterator i = d.iterator();
  System.out.println(i.hasNext());
  while(i.hasNext()){
   System.out.println(i.next());
  }


 }

}
 

Комментарии:

1. Deque — ужасное имя класса, поскольку это java.util.Deque существующий интерфейс.

2. @Powerlord похоже, это задание из некоторых алгоритмов или курса программирования на Java :).

Ответ №1:

У вас есть это определение вашего класса:

 private class DequeIterator implements Iterator<Item>{
    Node current=after.next;
    //rest of code
}
 

Вы определяете, что current узел является следующим узлом after , который имеет null значение и after является последним элементом в вашем двусвязном списке, который будет null , таким образом, выполнение любой операции с использованием current приведет к a NullPointerException .

Решение: определить current как before .

Комментарии:

1. Спасибо, это была проблема