Multitasking Objects: Reasonable Solution

// From solution by hsingh

import java.io.*;
import java.lang.*;
import java.util.*;

class runMe
{
   public static void main (String[] args)
   {
      Controller c = new Controller();
      c.add (new MultiTaskObject ("first", 1));
      c.add ( new MultiTaskObject ("second", 1));
      c.add ( new MultiTaskObject ("third", 1));
      c.startIt ();
   }
}

abstract class TaskObject extends Object implements Runnable
{
   int currentNum;
   String name;
   Thread runner=null;

   synchronized public void setAndSwap ()
   {
      notify ();
      try { wait (); } catch (Exception e) {}
   }

   synchronized public void get ()
   {
      if (runner == null)
      {
         runner = new Thread (this);
         runner.start ();
      }
      notify ();
      try { wait(); } catch (Exception e) {}
   }
}

class MultiTaskObject extends TaskObject
{
   public MultiTaskObject (String name, int start)
   {
      super.currentNum = start;
      this.name = name;
   }
  
   public void run ()
   {
      while (true)
      {
         System.out.println ("ID: "+name+" value = "+(currentNum++));
         setAndSwap ();
      }
   }
}

class Controller implements Runnable
{
   Vector myQ;
   int index;
   Thread runner=null;

   public Controller ()
   {
      myQ = new Vector ();
      index = 0;
   }
  
   public void startIt ()
   {
      runner = new Thread (this);
      runner.start ();
   }
  
   public void add (Object my)
   {
      myQ.addElement (my);
   }
  
   public void remove (String toRemove)
   {
      int index;
      index = locateIndex (toRemove);
      if (index!=-1)  //Sanity Check
         myQ.removeElementAt(index);
   }
  
   public void remove (int ind)
   {
      myQ.removeElementAt (ind);
   }
  
   public void setOrder (String before, String after)
   {
      int bef, aft;
    
      bef = locateIndex (before);
      aft = locateIndex (after);
      if ((bef == -1)||(aft == -1)) //Sanity Check
      return; 
      TaskObject obj = (TaskObject)myQ.elementAt (aft);
      remove (aft);
      myQ.insertElementAt (obj, (bef+1));
      index = 0; // to make sure that we start from the first element again
   }

   public int locateIndex (String toLookFor)
   {
      int i;
      TaskObject tmp;

      for (i=0 ; i < myQ.size() ; i++)
      {
         tmp = (TaskObject)myQ.elementAt(i);
         if(toLookFor == tmp.name) return i;
      }
      return -1;
   }
  
   public void next ()
   {
      TaskObject tmp;
      if ((index) >= myQ.size()) index=0;
      tmp = (TaskObject)myQ.elementAt (index);
      tmp.get();
      index++;
   }

   public void run ()
   {
      int i;
      System.out.println ("Printing 10 values each: Order is: first second Third");
      for (i=0 ; i < 30 ; i++) { next(); }

      System.out.println ("-----------------");
      setOrder ("first","third");
      System.out.println ("Changing Order");
      System.out.println ("Printing 10 values each: Order is: first Third Second");
      for (i=0 ; i < 30 ; i++) { next(); }
    
      System.out.println ("------------------");
      System.out.println ("Removing element third");
      remove ("third");
      System.out.println ("Printing 10 values each: Order is: first second");
      for (i=0 ; i < 20 ; i++) { next(); }
 
      System.out.println ("-------------------");   
      System.out.println ("Adding elements fourth");
      add (new MultiTaskObject ("fourth", 1));
      System.out.println ("Setting Order : first fourth");
      setOrder ("first", "fourth");
      System.out.println ("Printing 10 values each: Order first fourth second");
      for (i=0 ; i < 30 ; i++) { next(); }    
  }
}