A steque is a stack-ended queue which is a data type that implements push, pop, and enqueue along with any other features that you wish to add to.
Note that I am implementing the steque with linked-list-based approach. Below is the code for my entire Steque class, the problem I have is whenever I try popping some element from the steque or to iterate through it I get the NullPointerException. The push() and enqueue() method seem to work just fine as I tested and I did thoroughly check my pop() and iterator() but can't seem to find any possible errors that might cause any NullPointerException. Any help on my code as how to resolve this will be greatly appreciated!
public class Steque<Item> implements Iterable<Item> {
private int N;
private Node first;
private Node last;
private class Node {
private Item item;
private Node next;
private Node prev;
}
/**
* create an empty steque
*/
public Steque() {
N = 0;
first = null;
last = null;
}
/**
* pop (return) the first item on top of stack and modify first
* accordingly to refer to next node.
*/
public Item pop() {
if (isEmpty()) throw new RuntimeException("Steque underflow");
Item item = first.item;
first = first.next;
N--;
return item;
}
/**
* push item on top of the stack and modify the first pointer
* to refer to the newly added item.
*/
public void push(Item item) {
Node oldfirst = first;
Node first = new Node();
first.item = item;
first.next = oldfirst;
if (oldfirst != null)
oldfirst.prev = first;
++N;
}
/**
* push item on bottom of the stack and reset the last pointer
* to refer to the newly added item.
*/
public void enqueue(Item item) {
Node oldlast = last;
Node last = new Node();
last.item = item;
last.prev = oldlast;
if (oldlast != null)
oldlast.next = last;
++N;
}
public Item peek() {
if (isEmpty()) throw new RuntimeException("Steque underflow");
return first.item;
}
public boolean isEmpty() {
return N == 0;
}
public int size() {
return N;
}
/**
* prints the steque from top to bottom
private void printState() {
System.out.println("Printing steque below: top --> bottom ");
for (Node idx = this.first; idx!= null; idx = idx.next) {
System.out.print(idx.item + " - ");
}
System.out.println();
}
*/
public String toString() {
StringBuilder s = new StringBuilder();
for (Item i : this) {
s.append(i + " ");
}
return s.toString().trim();
}
public Iterator iterator() {
return new LIFOIterator();
}
/**
* iterator that implements hasNext(), next(), and remove().
*/
private class LIFOIterator implements Iterator<Item>
{ // support LIFO iteration
private Node current = first;
public boolean hasNext() { return current.next != null; }
public void remove() {
Node n = first;
while (n.next.next != null) {
n = n.next;
}
n.next = null;
--N;
}
public Item next() {
if (!hasNext())
throw new NoSuchElementException();
Item item = current.item;
current = current.next;
return item;
}
}
/**
* a simple test client
*/
public static void main(String[] args) {
Steque<String> steq = new Steque<String>();
while (!StdIn.isEmpty()) {
String item = StdIn.readString();
if (!item.equals("-")) {
//steq.push(item);
steq.enqueue(item);
}
/*
else if (!steq.isEmpty()) {
System.out.print(steq.pop() + " ");
}
*/
}
System.out.println("(" + steq.size() + " left on steque)");
Iterator itr = steq.iterator();
System.out.println("printing steque of strins below: ");
while(itr.hasNext()) {
System.out.print(itr.next() + " ");
}
}
}
Note: I am omitting all the import statements here but they are indeed included in my program so there is guaranteed to be no "undefined method" or "undeclared identifier" error in this code.
The problem is, that your first variable does not get filled when you only use the enqueue method.
Therefore the methods that access this field fire an NPE.
hasNext uses the field via current.
IMO the solution would be to catch the special for N == 0 in enqeue and fill the first element with the available element.
I tried
if(N==0)
first = last
after the initialisation of last in enqeue and it works without NPE.
Related
Been banging my head against a wall for a week and cannot seem to get anywhere. I want to be able to get the max from the stack and keep it in the stack so in the end there is a only one value in the Stack and that is the max. I believe my algorithm to keep the max is correct, but I think my pop method is malfunctioning and I cannot figure out why. Any guidance is appreciated. Both files I am working with are included
import java.io.File;
import java.io.IOException;
import java.util.ListIterator;
import java.util.Random;
public class LinkedListStack {
DoublyLinkedList<Integer> list = new DoublyLinkedList<Integer>();
public int size() {
if (list.isEmpty()) {
System.out.println("Stack is empty");
}
return list.size();
}
public void push(Integer s) {
list.add(s);
}
public Integer pop() {
/* need help with this method */
}
public Integer top() {
return list.iterator().next();
}
public boolean isEmpty() {
return list.isEmpty();
}
public String displayStack() {
return (list.toString());
}
public static void main(String[] args) throws IOException {
LinkedListStack stack = new LinkedListStack();
int n, seed;
File outputFile;
File dir = new File(".");
if (args.length > 0) {
n = Integer.parseInt(args[0]);
seed = Integer.parseInt(args[1]);
}else {
n = 10;
seed = 1;
}
if (args.length == 3) {
outputFile = new File(args[2]);
} else {
outputFile = new File(dir.getCanonicalPath() + File.separator + "Files/testOut_Stack");
}
OutputWriter out = new OutputWriter(outputFile);
Random r = new Random(seed);
Integer nextval;
for (int i = 0; i < n; i++) {
nextval = r.nextInt(10000);
if (stack.isEmpty()) {
stack.push(nextval);
}
if (nextval > stack.top()) {
stack.pop();
stack.push(nextval);
}
/* retain the max value that you see among the integers generated in the stack.
* In the end there should be only one integer in stack, which is the max value
*/
}
// write the content of stack -- which is the max value -- to file
out.writeOutput(stack.displayStack());
}
}
import java.io.File;
import java.io.IOException;
import java.util.ListIterator;
import java.util.NoSuchElementException;
import java.util.Random;
import csci3230.hw3.OutputWriter;
public class DoublyLinkedList<Item> implements Iterable<Item> {
private int n; // number of elements on list
private Node pre; // sentinel before first item
private Node post; // sentinel after last item
public DoublyLinkedList() {
pre = new Node();
post = new Node();
pre.next = post;
post.prev = pre;
}
// linked list node helper data type
private class Node {
private Item item;
private Node next;
private Node prev;
}
public boolean isEmpty() {
return (n == 0);
// your code
}
public int size() {
return n;
// your code
}
// add the item to the list
public void add(Item item) {
Node last = post.prev;
Node x = new Node();
x.item = item;
x.next = post;
x.prev = last;
post.prev = x;
last.next = x;
n++;
// your code
}
public ListIterator<Item> iterator() { return new DoublyLinkedListIterator(); }
// assumes no calls to DoublyLinkedList.add() during iteration
private class DoublyLinkedListIterator implements ListIterator<Item> {
private Node current = pre.next; // the node that is returned by next()
private Node lastAccessed = null; // the last node to be returned by prev() or next()
// reset to null upon intervening remove() or add()
private int index = 0;
public boolean hasNext() {
return (index < n); // your code
}
public boolean hasPrevious() {
return (index > 0);
// your code
}
public int previousIndex() {
return (index - 1);
// your code
}
public int nextIndex() {
return (index + 1);
// your code
}
public Item next() {
if (!hasNext()) throw new NoSuchElementException();
lastAccessed = current;
Item item = current.item;
current = current.next;
index++;
return item;
// your code
}
public Item previous() {
if (!hasPrevious()) throw new NoSuchElementException();
current = current.prev;
index--;
lastAccessed = current;
return current.item;
// your code
}
// replace the item of the element that was last accessed by next() or previous()
// condition: no calls to remove() or add() after last call to next() or previous()
public void set(Item item) {
if (lastAccessed == null) throw new IllegalStateException();
lastAccessed.item = item;
// your code
}
// remove the element that was last accessed by next() or previous()
// condition: no calls to remove() or add() after last call to next() or previous()
public void remove() {
if (lastAccessed == null) throw new IllegalStateException();
Node x = lastAccessed.prev;
Node y = lastAccessed.next;
x.next = y;
y .prev = x;
n--;
if (current == lastAccessed) {
current = y;
}
else {
index--;
}
lastAccessed = null;
// your code
}
// add element to list
public void add(Item item) {
Node x = current.prev;
Node y = new Node();
Node z = current;
y.item = item;
x.next = y;
y.next = z;
z.prev = y;
y.prev = x;
n++;
index++;
lastAccessed = null;
// your code
}
}
public String toString() {
StringBuilder s = new StringBuilder();
for (Item item : this)
s.append(item + " ");
return s.toString();
}
}
You can keep the first integer you pop as a temporary "largestValue" and compare every subsequent integer you pop with it to see whether you should replace it. At the very of your function, pop all values and add the largestValue back onto it.
I am new in java. I have been trying to do some tests while teaching myself the language. Now I am on a linked list implementation. I chucked the code from test samples online. There are two files, LinkedList and LinkedListIterator. I am alright understanding the implementation. However, I would like to add to methods to the LinkedList class. One method (getString()) will be used to display a concatenation of all the string variables in the linkedlist. The second method getSize() will be used to display the size of the list. I have trouble getting the current instance of the linkedlist so I can iterate and get the strings and size. Can someone please assist? Help will be really appreciated.
The two files are as below:
import java.util.NoSuchElementException;
public class LinkedList
{
//nested class to represent a node
private class Node
{
public Object data;
public Node next;
}
//only instance variable that points to the first node.
private Node first;
// Constructs an empty linked list.
public LinkedList()
{
first = null;
}
// Returns the first element in the linked list.
public Object getFirst()
{
if (first == null)
{
NoSuchElementException ex
= new NoSuchElementException();
throw ex;
}
else
return first.data;
}
// Removes the first element in the linked list.
public Object removeFirst()
{
if (first == null)
{
NoSuchElementException ex = new NoSuchElementException();
throw ex;
}
else
{
Object element = first.data;
first = first.next; //change the reference since it's removed.
return element;
}
}
// Adds an element to the front of the linked list.
public void addFirst(Object element)
{
//create a new node
Node newNode = new Node();
newNode.data = element;
newNode.next = first;
//change the first reference to the new node.
first = newNode;
}
// Returns an iterator for iterating through this list.
public ListIterator listIterator()
{
return new LinkedListIterator();
}
public String toString(){
}
public int getSize(){
return this.size();
}
//nested class to define its iterator
private class LinkedListIterator implements ListIterator
{
private Node position; //current position
private Node previous; //it is used for remove() method
// Constructs an iterator that points to the front
// of the linked list.
public LinkedListIterator()
{
position = null;
previous = null;
}
// Tests if there is an element after the iterator position.
public boolean hasNext()
{
if (position == null) //not traversed yet
{
if (first != null)
return true;
else
return false;
}
else
{
if (position.next != null)
return true;
else
return false;
}
}
// Moves the iterator past the next element, and returns
// the traversed element's data.
public Object next()
{
if (!hasNext())
{
NoSuchElementException ex = new NoSuchElementException();
throw ex;
}
else
{
previous = position; // Remember for remove
if (position == null)
position = first;
else
position = position.next;
return position.data;
}
}
// Adds an element before the iterator position
// and moves the iterator past the inserted element.
public void add(Object element)
{
if (position == null) //never traversed yet
{
addFirst(element);
position = first;
}
else
{
//making a new node to add
Node newNode = new Node();
newNode.data = element;
newNode.next = position.next;
//change the link to insert the new node
position.next = newNode;
//move the position forward to the new node
position = newNode;
}
//this means that we cannot call remove() right after add()
previous = position;
}
// Removes the last traversed element. This method may
// only be called after a call to the next() method.
public void remove()
{
if (previous == position) //not after next() is called
{
IllegalStateException ex = new IllegalStateException();
throw ex;
}
else
{
if (position == first)
{
removeFirst();
}
else
{
previous.next = position.next; //removing
}
//stepping back
//this also means that remove() cannot be called twice in a row.
position = previous;
}
}
// Sets the last traversed element to a different value.
public void set(Object element)
{
if (position == null)
{
NoSuchElementException ex = new NoSuchElementException();
throw ex;
}
else
position.data = element;
}
} //end of LinkedListIterator class
}
LinkedListIterator class:
public interface ListIterator
{
//Move Moves the iterator past the next element.
Object next();
// Tests if there is an element after the iterator position.
boolean hasNext();
// Adds an element before the iterator position
// and moves the iterator past the inserted element.
void add(Object element);
// Removes the last traversed element. This method may
// only be called after a call to the next() method.
void remove();
// Sets the last traversed element to a different value.
void set(Object element);
}
Error when I try the implmentation of getSize():
Exception in thread "main" java.lang.StackOverflowError
at assignment10.LinkedList.size(LinkedList.java:84)
at assignment10.LinkedList.size(LinkedList.java:84)
at assignment10.LinkedList.size(LinkedList.java:84)
at assignment10.LinkedList.size(LinkedList.java:84)
The getSize() could be
public int getSize(){
int size = 0;
ListIterator iterator = listIterator();
while(iterator.hasNext()) {
iterator.next();
size++;
}
return size;
}
But it is not efficient to iterate over list each time to knowe it's size. The better solution is to store size as class variable and increase or decrease in methods modifying list.
The idea of toString() method is the same, iterate over the list and append each item to the result string
public String toString(){
StringBuilder sb = new StringBuilder();
ListIterator iterator = listIterator();
while(iterator.hasNext()) {
sb.append(String.valueOf(iterator.next())).append(",");
}
return sb.toString;
}
I'm trying to implement the a Stack in Java with a circular singly linked list as the underlying data structure. I placed the insert function for a circular linked list in replacement of the push function for the stack and so on. I don't have any errors but I'm having troubles displaying the stack. If anyone could point me in the right direction of how to display the stack or what's going wrong I'd really appreciate it!
Here is my stack class:
public class Stack {
private int maxSize; // size of stack array
private long[] stackArray;
private int top; // top of stack
private Node current = null; // reference to current node
private int count = 0; // # of nodes on list
private long iData;
public Stack(int s) // constructor
{
maxSize = s; // set array size
stackArray = new long[maxSize]; // create array
top = -1; // no items yet
}
public void push(long j) // put item on top of stack
{
Node n = new Node(j);
if(isEmpty()){
current = n;
}
n.next = current;
current = n;
count++;
}
//--------------------------------------------------------------
public Node pop() // take item from top of stack
{
if(isEmpty()) {
return null;
}
else if(count == 1){
current.next = null;
current = null;
count--;
return null;
}else{
Node temp = current;
current = current.next;
temp.next = null;
temp = null;
count--;
}
return current;
}
//--------------------------------------------------------------
public Node peek(long key) // peek at top of stack
{
Node head = current;
while(head.iData != key){
head = head.next;
}
return head;
}
//--------------------------------------------------------------
public boolean isEmpty() // true if stack is empty
{
return (count == 0);
}
//--------------------------------------------------------------
public boolean isFull() // true if stack is full
{
return (count == maxSize-1);
}
//--------------------------------------------------------------
Here is my constructor class
public class Node{
public long iData; // data item (key)
public Node next; // next node in the list
public Node(long id){ // constructor
iData = id; // next automatically nulls
}
public void displayNode(){
System.out.print(iData + " ");
}
public static void main(String[] args) {
Stack newlist = new Stack(3);
newlist.push(1);
newlist.push(2);
newlist.push(3);
newlist.push(4);
newlist.pop();
newlist.pop();
newlist.push(4);
newlist.pop();
newlist.peek(1);
newlist.push(5);
while( !newlist.isEmpty() ) // until it’s empty,
{ // delete item from stack
Node value = newlist.pop();
System.out.print(value); // display it
System.out.print(" ");
} // end while
System.out.println("");
}
//newlist.displayList();
}
First, in your main function you are printing value using System.out.print function. This displays the object's class name representation, then "#" followed by its hashcode.
Replace following lines
System.out.print(value); // display it
System.out.print(" ");
with
value.displayNode();
Second, in pop method, you are returning null when count is 1. It should return the last element which is present in the list. Also, in last else if clause, you should return temp. Replace your code with this.
public Node pop() // take item from top of stack
{
if (isEmpty()) {
return null;
}
Node temp = current;
if (count == 1) {
current = null;
} else {
current = current.next;
}
count--;
temp.next = null;
return temp;
}
A few notes on your implementation:
1) stackArray member seems to be a leftover from another array based stack implementation.
2) is max size really a requirement? if so, you don't enforce the stack size limitation in push(..)
3) Your push(..) method doesn't keep the list circular. You should close the loop back to the new node.
4) Adding a dummy node allows you to keep the linked list circular, regardless of the stack size. This can make your push(..) method simpler (as well as any iteration for printing purposes for example)
5) The peek() method contract is unclear. Usually you want the peek method to return the value in the top of the stack, without removing it. Also, why do you return type Node? This class should be hidden from the caller - it's an internal implementation detail, not something you want to expose in your API.
Following is an alternative implementation, that also supports toString():
public class Stack {
private Node EOS;
private int count = 0;
public Stack() {
EOS = new Node(0);
EOS.next = EOS;
}
public void push(long j) {
Node newNode = new Node(j);
Node tmp = EOS.next;
EOS.next = newNode;
newNode.next = tmp;
count++;
}
public Long pop() {
if (isEmpty()) {
return null;
} else {
count--;
Node node = EOS.next;
EOS.next = node.next;
return node.iData;
}
}
public Long peek() {
if (isEmpty()) {
return null;
} else {
Node node = EOS.next;
return node.iData;
}
}
public boolean isEmpty() {
return (count == 0);
}
#Override
public String toString() {
StringBuilder sb = new StringBuilder();
Node p = EOS.next;
while (p != EOS) {
sb.append(p).append("\n");
p = p.next;
}
return sb.toString();
}
private static class Node {
public long iData;
public Node next;
public Node(long id) {
iData = id;
}
#Override
public String toString() {
return "<" + iData + ">";
}
}
}
I am writing a generic data structure that can add and delete from the first or last nodes
I tested my code however I got exceptions in some certain way of input.
now if I addlast then addfirst then removelast i got exception
and when I addfirst many time without adding last then try to remove them by removelast() function i got exception
but when I addlast many time without adding first then remove them by removefirst() it works
I am trying to avoid while loops here is the code
import java.util.Iterator;
public class Deque <Item> implements Iterable <Item> {
private Node first,last;
private class Node
{
Item item;
Node next;
Node prev;
}
public Deque()
{
first = null;
last = null;
}
public boolean IsEmpty()
{
return first == null;
}
public void addFirst(Item item)
{
Node oldfirst = first;
first = new Node();
first.item = item;
first.next = oldfirst;
first.prev = null;
if (last == null)
{
last = first;
}
}
public void addlast(Item item)
{
Node oldlast = last;
last = new Node();
last.item = item;
last.next = null;
if (first == null)
{
first = last;
}
else
{
last.prev = oldlast;
oldlast.next = last;
}
}
public Item removeFirst()
{
Item x = first.item;
first = first.next;
if (IsEmpty())
last = null;
return x;
}
public Item removeLast()
{
if (first == last)
return removeFirst();
Item x = last.item;
last = last.prev;
last.next = null;
if (IsEmpty())
first = null;
return x;
}
public Iterator<Item> iterator ()
{
return new ListIterator();
}
private class ListIterator implements Iterator<Item>
{
private Node current = first;
public boolean hasNext ()
{
return current != null;
}
public void remove()
{
//NOt Supported
}
public Item next()
{
Item x = current.item;
current = current.next;
return x;
}
}
}
I believe I have something wrong with last.prev in removelast() since it is already null and then referred last = last.perv in remove()
but i couldnt think of a way to link last to last node of first
can anyone help me with this
here is the main if you want to try...
public class Main {
/**
* #param args
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
Deque<Integer> o = new Deque<Integer>();
int num = 0;
while (true)
{
StdOut.println("enter 1 to addfirst, 2 addlast, 3 removefirst, 4 removelast, " +
"5 to exit");
num = StdIn.readInt();
if (num == 5)
break;
switch (num)
{
case 1:
StdOut.println("enter number to add first");
int x = StdIn.readInt();
o.addFirst(x);
break;
case 2:
StdOut.println("enter number to add last");
int y = StdIn.readInt();
o.addlast(y);
break;
case 3:
int w=o.removeFirst();
StdOut.print("the deleted number is: ");
StdOut.print(w);
StdOut.println();
break;
case 4:
int z=o.removeLast();
StdOut.print("the deleted number is: ");
StdOut.print(z);
StdOut.println();
break;
default:
StdOut.println("Stick with the range!");
break;
}
for (Iterator<Integer> i=o.iterator(); i.hasNext();)
{
StdOut.print(i.next());
StdOut.print(" ");
}
StdOut.println();
}
}
}
You have missed a couple of operations. In addFirst you don't set oldFirst.prev = first;, so if you add nodes with it, you won't have any prev references defined. That is why removeLast fails. It attempts to clean traverse to last.prev, but since everything was added with addFirst, last.prev is null.
Also, in removeFirst, you have a similar issue, that you don't remove the link to the former prev node, such as first.prev = null; Without doing that, if you were traversing using prev references, you would be able to move beyond the first node, after having called removeFirst.
addLast and addFirst should do, in essence, exactly the same things, just at different ends of the list. addFirst looks simpler, in your implementation, which means either you missed something in addFirst, or addLast is overly complex. In this case, you missed something in addFirst. Same with the remove methods.
Closed. This question does not meet Stack Overflow guidelines. It is not currently accepting answers.
Questions concerning problems with code you've written must describe the specific problem — and include valid code to reproduce it — in the question itself. See SSCCE.org for guidance.
Closed 9 years ago.
Improve this question
I am working on some code in Java that is supposed to implement the well-known
Josephus problem using a Circular Linked List. Here is some information on the Josephus
problem: http://en.wikipedia.org/wiki/Josephus_problem
I have a Student class and Driver class that have been given to me to create my Josephus class.
Here is the Student class: http://pastebin.com/4YgSA7CM
Here is the Driver class: http://pastebin.com/Nb08Dtqk
Neither of these classes can be modified.
I had to start from scratch and make a Josephus class that uses a Circular Linked List that effectively uses the Josephus problem.
Here is my completed Josephus class with no compiler errors:
/** Implementation of Josephus problem. The Josephus problem
is named after the historian Flavius Josephus. For more
information on this problem visit:
http://en.wikipedia.org/wiki/Josephus_problem
*/
import java.util.ListIterator;
import java.util.NoSuchElementException;
import java.util.ArrayList;
public class Josephus <E> {
private Node<E> head;
private int count; // number of elements in the list
/** Constructs an empty Josephus circle */
// Complexity O(1)
public Josephus() {
head = null;
count = 0;
}
/** Constructs an Josephus circle by adding the
elements from an arraylist
#param array The ArrayList of items of type E
*/
// Complexity: O(n)
public Josephus(ArrayList<E> array) {
head = null;
for (int i = 0; i < array.size(); i++)
add(array.get(i));
}
/** Inserts the specified element in the list at the
last position
#param dataItem the element to add
*/
// Complexity O(1)
#SuppressWarnings({ "unchecked" })
public void add(E dataItem) {
Node <E> node = new Node <E> (dataItem, null, null);
if (count == 0) // list is empty
head = node.previous= node ;
else
head.previous.next = node;
node.previous = head.previous;
head.previous = node;
count++;
}
// To be completed by the student
/** Inserts the specified element in the list at the
end. This method has the same behavior as add(E)
#param dataItem the element to add at the end
*/
// Complexity O(1)
public void addLast(E dataItem) {
add(dataItem);
}
/** Inserts the element at the beginning of the list
#param dataItem The element to be added
*/
// Complexity O(1)
public void addFirst(E dataItem) {
Node<E> node = new Node <E>(dataItem, null, null);
// To be completed by the student
if (head == null) // list is empty
head = head.previous = node;
else {
node.next = head;
head.previous = node;
head = node;
}
count++;
}
/** removes the element from the beginning of the list
#return The element that was remvoed
#throws NoSuchElementException if the list is empty
*/
// Complexity O(1)
public E removeFirst() {
// To be completed by the student
if (head != null) {
E item = head.data;
if (head == head.previous) // list has only one element
head = head.previous = null;
else { // list has more than 1 element
head = head.next;
head.previous = null;
}
count--;
return item;
}
else throw new NoSuchElementException();
}
/** removes the element from the end of the list
#return The element that was remvoed
#throws NoSuchElementException if the list is empty
*/
// Complexity O(1)
public E removeLast() {
// to be completed by the student
if (head.previous != null) {
E item = head.previous.data;
if (head == head.previous) // list has only one item
head = head.previous = null;
else { // list has more than one element
head.previous = (head.previous).previous;
head.previous.next = null;
}
count--;
return item;
}
else throw new NoSuchElementException();
}
/** returns a reference to the element at
position index
#param index The index of the element being sought
#return A reference to the element at position index
#throws IndexOutOfBoundsException if index is out of range
*/
// Complexity O(n)
public E get(int index) {
if ((index < 0) || (index >= count))
throw new IndexOutOfBoundsException(Integer.toString(index));
Node<E> temp = head;
for (int i = 0; i < index; i++)
temp = temp.next;
return temp.data;
}
/** Sets the element at position index to reference
anEntry.
#param index The position of the element that is to
be set
#param anEntry The new value at position index
#return the element that was previously at position index
#throws IndexOutOfBoundsException if index is out of range
*/
// Complexity O(n)
public E set(int index, E anEntry) {
if ((index < 0) || (index >= count))
throw new IndexOutOfBoundsException(Integer.toString(index));
Node<E> temp = head;
for (int i = 0; i < index; i++)
temp = temp.next;
E result = temp.data;
temp.data = anEntry;
return result;
}
/** Inserts the specified element in the list at a
given index
#param index The position at which the new element
has to be inserted
#param anEntry The element to add
#throws IndexOutOfBoundsException if index is out of range
*/
// Complexity O(n)
public void add(int index, E anEntry) {
// To be completed by the student
if ((index < 0) || (index > count))
throw new IndexOutOfBoundsException(Integer.toString(index));
if (index == 0) addFirst(anEntry);
else if (index == count) addLast(anEntry);
else {
Node <E> node = head;
int i = 0;
while(node!=null && i<index){
i++;
node = node.next;
}
Node<E> newNode = new Node <E> (anEntry, node, node.next);
node.next.previous = newNode;
node.next = newNode;
count++;
}
}
/** searches for target and returns the position of the
first occurrence, or -1 if it is not in the list
#param target The element we are searching for
#return The position of target if found; -1 if not found
*/
// Complexity O(n)
public int indexOf(E target) {
Node<E> temp = head;
for (int i = 0; i < count; i++) {
if (temp.data.equals(target)) return i;
temp = temp.next;
}
return -1;
}
/** removes the element at position index
#param index The index of the element to be removed
#return The element that was removed
#throws IndexOutOfBoundsException if index is invalid
*/
// Complexity O(n)
public E remove(int index) {
// to be completed by the student
if ((index < 0) || (index >= count))
throw new IndexOutOfBoundsException(Integer.toString(index));
Node<E> temp = head;
for(int i =0;i<index; i++)
temp = temp.next;
E result = temp.data;
temp.next = temp.previous;
return result;
}
/** sets the start position for the Josephus game
#param index The starting position
#throws IndexOutOfBoundsException if index is invalid
*/
// Complexity O(n)
public void setStartPosition(int index) {
if ((index < 0) || (index >= count))
throw new IndexOutOfBoundsException(Integer.toString(index));
for (int i = 0; i < index; i++)
head = head.next;
}
/* This private utility method is used in startJosephus
method.
Complexity O(1)
*/
private void removeAfter(Node<E> node) {
node.next = node.next.next;
node.next.previous = node;
count--;
}
/** simulates the Josephus game by killing every other person
until the winner is the only one left.
#return The survivor of the game
*/
public E startJosephus() {
E item =head.data;
if(head.next != null){
if(head == head.previous)
return item;
else
while(count>1);
removeAfter(head);
head =head.next;
}
return item;
}
/** Returns a list-iterator of the elements in this list
(in proper sequence), starting at the beginning
of the list.
*/
public ListIterator <E> iterator() {
return new myIterator();
}
/** #return The number of elements in the list
*/
public int size() {
return count;
}
// this is an inner clss implementing the ListIterator
// interface.
// visit http://docs.oracle.com/javase/1.4.2/docs/api/java/util/ListIterator.html
// for a complete list of methods in ListIterator
private class myIterator implements ListIterator <E> {
private Node<E> forward = head;
private Node<E> backward = head;
private boolean firstTime = true;
/** checks if a current item E is the last
in the collection
*/
public boolean hasNext() {
return (forward != null);
}
/** returns the next item in the collection if
there is one. If there is no more items
throws NoSuchElementException
*/
public E next() {
if (forward == null) throw
new NoSuchElementException();
else {
E item = forward.data;
forward = forward.next;
if (forward == head) forward = null;
return item;
}
}
/** checks if a current item is the first
in the collection
*/
public boolean hasPrevious() {
return (backward != null);
}
/** returns the previous item in the collection if
there is one. If there is no more items
throws NoSuchElementException
*/
public E previous() {
if (backward == null) throw
new NoSuchElementException();
else {
if (firstTime) {
backward = backward.previous;
firstTime = false;
}
E item = backward.data;
backward = backward.previous;
if (backward == head.previous) backward = null;
return item;
}
}
/* this operation is not supported */
public void add(E obj) {
throw new UnsupportedOperationException();
}
/* this operation is not supported */
public void set(E obj) {
throw new UnsupportedOperationException();
}
/* this operation is not supported */
public int previousIndex() {
throw new UnsupportedOperationException();
}
/* this operation is not supported */
public int nextIndex() {
throw new UnsupportedOperationException();
}
/* this operation is not supported */
public void remove() {
throw new UnsupportedOperationException();
}
}
private static class Node <E> {
private E data;
private Node<E> next;
private Node<E> previous;
/** constructor Creates an empty node with both next and
previous fields set to be null
#param dataItem - item to be inserted
*/
private Node(E dataItem) {
data= dataItem;
previous = next = null;
}
/** creates a new node that references another node
#param dataItem The data stored
#param previousNodeRef The node previous to this node
#param nextNodeRef The node next to this node
*/
private Node(E dataItem, Node<E> previousNodeRef, Node <E> nextNodeRef ) {
data = dataItem;
previous = previousNodeRef;
next = nextNodeRef;
}
}
}
My startJosephus method is the main problem I believe. Not completely sure though. Here is the startJosephus method specifically within that above code:
/** simulates the Josephus game by killing every other person
until the winner is the only one left.
#return The survivor of the game
*/
public E startJosephus() {
E item =head.data;
if(head.next != null){
if(head == head.previous)
return item;
else
while(count>1);
removeAfter(head);
head =head.next;
}
return item;
}
Here is what is running when I run my Josephus class: http://pastebin.com/5GnChgYd
Here is what the output is supposed to produce: http://pastebin.com/Qr5dCZJp
Also, here are the two input files used to produce this output:
StudentList1.txt: http://pastebin.com/ysjevQ8u
StudentList2.txt: http://pastebin.com/r2YeppNm
Based on the output I am getting and the output I am supposed to be getting, it appears the Josephus problem is not starting and simulating the killing spree. However, I do not know what is wrong with my code. My code cannot have a tail since it is a Circular Linked List. Any idea as to what I am doing wrong here? Sorry for all the Pastebin links, it just seemed like a better way to organize all of the code I am presenting here. Hope to hear your thoughts.
EDIT:
There are 21 persons in this list
The game starts with McElroy,Breanna at starting position
The killing spree begins......
The sole survivor at the end of this gruesome game is McElroy,Breanna
Exception in thread "main" java.lang.NullPointerException
at Josephus$Node.access$5(Josephus.java:383)
at Josephus.add(Josephus.java:49)
at Josephus.addLast(Josephus.java:66)
at Driver.main(Driver.java:96)
This is the new runtime errors I am getting after I fixed my problem with the infinite loop. Any suggestions???? What is with all of these Null Pointer Exceptions
if(head.next != null) {
if (head == head.previous)
return item;
else
while(count>1);
removeAfter(head);
head =head.next;
This piece of code will loop forever in all cases except when head.next is null or head == head.previous, which will always be true at the start of the game. Therefore, your program loops forever for anything but the trivial initial conditions. Obviously, you intended to write
if(head.next != null) {
if (head == head.previous)
return item;
else
while(count>1) {
removeAfter(head);
head =head.next;
}
I think you have an endless loop:
while (count > 1);