"Write a program to display a linked list graphically. Draw each element of the list as a box, and indicate the links with line segments. Draw an iterator as in Figure 15-3. Supply buttons to move the iterator and to add and remove elements."

The elements of the node appear as boxes, with a number in them, connected by lines. Much of teh following code was given to me, the parts I have written are the draw methods, as indicated by the question. So far when i run the program, the buttons show up, but not of them do anything. This is a lot of code, but I appreciate any help given.

package Question2;


import javax.swing.JFrame;

/**
   Displays a linked list.
*/
public class LinkedListViewer
{
   public static void main(String args[])
   {
      JFrame frame = new LinkedListFrame();
      frame.setTitle("LinkedListViewer");
      frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
      frame.setVisible(true);
   }
}
package Question2;
import java.awt.Graphics;
import java.awt.Graphics2D;
import	java.awt.Dimension;
import	java.awt.event.ActionEvent;
import	java.awt.event.ActionListener;
import	javax.swing.JButton;
import	javax.swing.JFrame;
import	javax.swing.JPanel;

public class LinkedListFrame extends JFrame
{
   public LinkedListFrame()
   {
      setSize(FRAME_WIDTH, FRAME_HEIGHT);
      JPanel panel = new JPanel();
      panel.add(makeButtonPanel ());
      component = new LinkedListComponent();
      component.setPreferredSize(new Dimension(
            COMPONENT_WIDTH, COMPONENT_HEIGHT));
      panel.add(component);
      add(panel);
   }

   private JPanel makeButtonPanel()
   {
      JPanel panel = new JPanel();

      addButton = new JButton("Add");
      addButton.addActionListener(new AddButtonListener());
      panel.add(addButton);

      newButton = new JButton("New Iter");
      newButton.addActionListener(new NewButtonListener());
      panel.add(newButton);

      nextButton = new JButton("Next");
      nextButton.addActionListener(new NextButtonListener());
      panel.add(nextButton);

      removeButton = new JButton("Remove");
      removeButton.addActionListener(new RemoveButtonListener());
      panel.add(removeButton);

      return panel;
   }

   class AddButtonListener implements ActionListener
   {
      public void actionPerformed(ActionEvent event)
      {
         component.add();
      }
   }
   
   class NewButtonListener implements ActionListener
   {
      public void actionPerformed(ActionEvent event)
      {
         component.newIterator();
      }
   }

   class NextButtonListener implements ActionListener
   {
      public void actionPerformed(ActionEvent event)
      {
         component.next();
      }
   }

   class RemoveButtonListener implements ActionListener
   {
      public void actionPerformed(ActionEvent event)
      {
         component. remove();
      }
   }
   
  

   private JButton newButton;
   private JButton nextButton;
   private JButton addButton;
   private JButton removeButton;
   private LinkedListComponent component;

   private static final int FRAME_WIDTH = 500;
   private static final int FRAME_HEIGHT = 400;
   private static final int COMPONENT_WIDTH = 500;
   private static final int COMPONENT_HEIGHT = 350;
}
package Question2;


import java.awt.Graphics;
import java.awt.Graphics2D;
import javax.swing.JComponent;

public class LinkedListComponent extends JComponent
{
   public LinkedListComponent()
   {
      list = new LinkedList();
      newIterator();
      next = 1;
   }

   public void newIterator()
   {
      iterator = (LinkedListIterator) list.listIterator();
      repaint();
      removeOk = false;
   }

   public void next()
   {
      if (iterator.hasNext())
      {
         iterator.next();
         repaint();
         removeOk = true;
      }
   }
   
   public void add()
   {
      iterator.add(new Integer(next));
      next++;
      repaint();
      removeOk = false;
   }

   public void remove()
   {
      if (removeOk)
      {
         iterator.remove();
         repaint();
         removeOk = false;
      }
   }
  
   public void paintComponent(Graphics g)
   {
      Graphics2D g2 = (Graphics2D) g;
      list.draw(g2);
      if (iterator != null)
         iterator.draw(g2);
   }
   private LinkedList list;
  private LinkedListIterator iterator;
   private int next = 1;
   private boolean removeOk = false;
}
package Question2;

import java.awt.Graphics2D;
import java.util.NoSuchElementException;

public class LinkedListIterator implements ListIterator
{
   /**
      Constructs an iterator that points to the front
      of the linked list.
   */
   public LinkedListIterator()
   {
      position = null;
      previous = null;
   }
   private class Node
   {  
      public Object data;
      public Node next;
   }
   /**
      Adds an element to the front of the linked list.
      @param element the element to add
   */
   public void addfirst(Object element)
   {  
      Node newNode = new Node();
      newNode.data = element;
      newNode.next = first;
      first = newNode;
   }
   /**
      Moves the iterator past the next element.
      @return the traversed element
   */
   public Object next()
   {
      if (!hasNext())
         throw new NoSuchElementException();
      previous = position; // Remember for remove
   
      if (position == null)
         position = first;
      else
         position = position. next;
   
      return position.data;
   }

   /**
      Tests if there is an element after the iterator
      position.
      @return true if there is an element after the iterator
      position
   */
   public boolean hasNext()
   {
      if (position == null)
         return first != null;
      else
         return position.next != null;
   }

   /**
      Adds an element before the iterator position
      and moves the iterator past the inserted element.
      @param element the element to add
   */
   public void add(Object element)
   {
      if (position == null)
      {
         addfirst(element);
         position = first;
      }
      else
      {
         Node newNode = new Node();
         newNode.data = element;
         newNode.next = position.next;
         position.next = newNode;
         position = newNode;
      }
      previous = position;
   }
   /**
      Removes the first element in the linked list.
      @return the removed element
   */
   public Object removefirst()
   {  
      if (first == null) 
         throw new NoSuchElementException();
      Object element = first.data;
      first = first.next;
      return element;
   }
   /**
      Removes the last traversed element. This method may
      only be called after a call to the next() method.
   */
   public void remove()
   {
      if (previous == position)
         throw new IllegalStateException();
   
      if (position == first)
      {
         removefirst();
      }
      else
      {
         previous.next = position.next;
      }
         position = previous;
      }
          
      /**
         Sets the last traversed element to a different
         value.
         @param element the element to set
      */
      public void set(Object element)
      {
         if (position == null)
            throw new NoSuchElementException();
         position. data = element;
      }
   
      public void draw(Graphics2D g2)
      {
         // TODO: Draw iterator
         LinkedList.draw(g2);
      }
     
      private Node position;
      private Node previous;
      private Node first;
   }
package Question2;
import java.awt.geom.Point2D;
import java.util.ArrayList;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Rectangle;
import java.awt.geom.Line2D;
import java.util.NoSuchElementException;

/**
   A linked list is a sequence of nodes with efficient
   element insertion and removal. This class
   contains a subset of the methods of the standard
   java.util.LinkedList class.
*/
public class LinkedList
{
   /**
      Constructs an empty linked list.
   */
   public LinkedList()
   {
      first = null;

   }

   /**
      Returns the first element in the linked list.
      @return the first element in the linked list
   */
   public Object getFirst()
   {
      if (first == null)
         throw new NoSuchElementException();
      return first.data;
   }

   /**
      Removes the first element in the linked list.
      @return the removed element
   */
   public Object removeFirst()
   {
      if (first == null)
         throw new NoSuchElementException();
      Object element = first.data;
      first = first.next;
      return element;

   }

   /**
      Adds an element to the front of the linked list.
      @param element the element to add
   */
   public void addfirst(Object element)
   {
      Node newNode = new Node();
      newNode.data = element;
      newNode.next = first;
      first = newNode;
   }

   /**
      Returns an iterator for iterating through this list.
      @return an iterator for iterating through this list
   */
   public ListIterator listIterator()
   {
      return new LinkedListIterator();
   }   

   public static void draw(Graphics2D g2)
   {
             
      // TODO: Draw all nodes
     for (int i = 0; i < count; i++)
     {

         Rectangle node = new Rectangle((int)(points.get(i).getX()), (int)(points.get(i).getY()), 30, 30);
         g2.draw(node);
     }

   }

          
   public static int count = 0;  
   public static ArrayList<Point2D.Double> points;
   private Node first;

   private class Node
   {

      public Node()
      {
         // TODO: Determine coordinates for this node
         if (LinkedList.count == 0)
         {
             LinkedList.points.add(new Point2D.Double(20, 20));
             LinkedList.count++;
         }
         else
         {
             LinkedList.points.add(new Point2D.Double(30 + points.get(LinkedList.count).getX(), 30 + points.get(LinkedList.count).getY()));
             LinkedList.count++;
         }
         
      }
   

   public Object data;
   public Node next;
   // TODO: Instance fields for coordinates(Done)

    
  }
  
}
package Question2;

/**
   A list iterator allows access of a position in a linked list.    
   This interface contains a subset of the methods of the 
   standard java.util.ListIterator interface. The methods for
   backward traversal are not included.
*/
public interface ListIterator
{  
   /**
      Moves the iterator past the next element.
      @return the traversed element
   */
   Object next();
      
   /**
      Tests if there is an element after the iterator 
      position.
      @return true 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.
      @param element the element to add
   */
   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. 
      @param element the element to set
   */
   void set(Object element);
}
Comments
Nice structured code

Hello LevelSix. I compress Your program to base size using java.util.LinkedList . It is functional. You can again try to grow it to use own LinkedListIterator,own LinkedList, own Node , function draw().

Some changes:
Graphics2D g2 = (Graphics2D) g.create(); in paintComponent(Graphics g)
public Dimension getPreferredSize() in LinkedListComponent
pack() in LinkedListViewer
important:
iterator = list.listIterator();
list.add(next++);

import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.util.Iterator;
import java.util.LinkedList;
import javax.swing.JComponent;

public class LinkedListComponent extends JComponent {

    private static final int COMPONENT_WIDTH = 500;
    private static final int COMPONENT_HEIGHT = 350;
    private java.util.LinkedList<Integer> list;
    private Iterator iterator;
    private int next = 0;
    private static final int delta = 10;

    public LinkedListComponent() {
        list = new java.util.LinkedList<Integer>();
        newIterator();
    }

    // also use frame.pack(); in main(...)
    @Override
    public Dimension getPreferredSize() {
        return new Dimension(COMPONENT_WIDTH, COMPONENT_HEIGHT);
    }

    public void newIterator() {
        System.out.println("newIterator()");
        iterator = list.listIterator();
        //other iterators
        //iterator = list.descendingIterator();
        //int startIndex = 5;
        //iterator = list.listIterator(startIndex);
        repaint();
    }

    public void next() {
        System.out.println("not impl.");
    }

    /**
     * add element to list
     */
    public void add() {
        System.out.println("add()");
        list.add(next++);
        repaint();
        System.out.println("list.size()=" + list.size());
    }

    /**
     * remove element from list
     */
    public void remove() {
        System.out.println("remove()");
        if (--next < 0) {
            next = 0;
        }
        System.out.println("next=" + next);
        if (list.isEmpty()) {
            return;
        }
        list.removeLast();
        repaint();
    }

    @Override
    public void paintComponent(Graphics g) {
        Graphics2D g2 = (Graphics2D) g.create();
        g2.setColor(Color.black);
        g2.draw3DRect(0, 0, COMPONENT_WIDTH - 1, COMPONENT_HEIGHT - 1, false);
        int previous = -1;
        for (Integer inner : list) {
            //for(Iterator i$ = list.iterator(); i$.hasNext();) {
            //Integer inner = (Integer)i$.next();
            g2.draw3DRect(delta + inner * 30, delta, 20, 20, false);
            g2.drawString("" + inner, 5 + delta + inner * 30, 15 + delta);
            if (previous != -1) {
                //g2.draw(Shape s);                
                g2.fill3DRect(20 + delta + previous * 30, delta + delta / 2, 10, 4, false);
            }
            previous = inner;
        }
        g2.dispose();
    }
}

quuba

Attachments LinkedListFrame.gif 3.41 KB

Is there a way to modify this code so that a elements that would go beyond the frame appear on a new line instead? And also so that the next button iterates the count inside the square, but does not affect their positioning?

I tried adding next++; to the next button, but doing so affects the positioning.

Also, what is the function of @Override?

@Override is an annotation in java 1.5 Tiger. In this case mean, that
public void paintComponent(Graphics g) is overrided. Look - LinkedListComponent extends JComponent , that original function paintComponent from JComponent is covered by my new definition. I'm user of NetBeans IDE. I strongly recomended to You work with NetBeans or Eclipse.
In paintComponent(Graphics g) we iterate throught list to display rectangles each time, when
JComponent needed refresh.
We need use an arrow to indicate where we are if we start manualy iterate step by step.
Iterator is an interface, and we can only ask i$.hasNext() and get value (Integer)i$.next().
Iterator NOT return info about size of list, or current index!
I try implement Next button

//ver. with Next button impl.
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.util.Iterator;
import java.util.LinkedList;
import javax.swing.JComponent;

public class LinkedListComponent extends JComponent {

    private static final int COMPONENT_WIDTH = 500;
    private static final int COMPONENT_HEIGHT = 350;
    private java.util.LinkedList<Integer> list;
    private Iterator iterator;
    private int next = 0;
    private static final int delta = 10;

    public LinkedListComponent() {
        list = new java.util.LinkedList<Integer>();
        newIterator();
    }

    // also use frame.pack(); in main(...)
    @Override
    public Dimension getPreferredSize() {
        return new Dimension(COMPONENT_WIDTH, COMPONENT_HEIGHT);
    }

    public void newIterator() {
        System.out.println("newIterator()");
        iterator = list.listIterator();
        //other iterators
        //iterator = list.descendingIterator();
        //int startIndex = 5;
        //iterator = list.listIterator(startIndex);
        repaint();
    }
    int valueReturnedByIterator = -1;

    public void next() {
        if (iterator.hasNext()) {
            System.out.println("iterator.next()");
            valueReturnedByIterator = (Integer) iterator.next(); //Line:44
        }
    }

    /**
     * add element to list
     */
    public void add() {
        System.out.println("add()");
        list.add(next++);
        repaint();
        System.out.println("list.size()=" + list.size());
    }

    /**
     * remove element from list
     */
    public void remove() {
        System.out.println("remove()");
        if (--next < 0) {
            next = 0;
        }
        System.out.println("next=" + next);
        if (list.isEmpty()) {
            return;
        }
        list.removeLast();
        repaint();
    }

    @Override
    public void paintComponent(Graphics g) {
        Graphics2D g2 = (Graphics2D) g.create();
        g2.setColor(Color.black);
        g2.draw3DRect(0, 0, COMPONENT_WIDTH - 1, COMPONENT_HEIGHT - 1, false);
        int previous = -1;
        for (Integer inner : list) {
            //for(Iterator i$ = list.iterator(); i$.hasNext();) {
            //Integer inner = (Integer)i$.next();
            g2.draw3DRect(delta + inner * 30, delta, 20, 20, false);
            g2.drawString("" + inner, 5 + delta + inner * 30, 15 + delta);
            if (previous != -1) {
                //g2.draw(Shape s);                
                g2.fill3DRect(20 + delta + previous * 30, delta + delta / 2, 10, 4, false);
            }
            previous = inner;
            /// 
            if (valueReturnedByIterator != -1) {
                g2.fill3DRect(15 + delta + valueReturnedByIterator * 30, delta + delta / 2, 10, 20, false);
            }
        }
        g2.dispose();
    }
}

but...

Exception in thread "AWT-EventQueue-0" java.util.ConcurrentModificationException
        at java.util.LinkedList$ListItr.checkForComodification(LinkedList.java:761)
        at java.util.LinkedList$ListItr.next(LinkedList.java:696)
        at question2.LinkedListComponent.next(LinkedListComponent.java:44)
        at question2.LinkedListFrame$NextButtonListener.actionPerformed(LinkedListFrame.java:72)

What is Your conclusion?
quuba

This article has been dead for over six months. Start a new discussion instead.