001    package lrs;
002    
003    /**
004     * Represents the abstract list state. Has a concrete toString () method that
005     * uses anynomous inner classes to compute the String representation of the
006     * LRStruct owner.
007     * @author Dung X. Nguyen and Stephen Wong  Copyright 2005 - All rights reserved.
008     * @author Mathias Ricken - Copyright 2008 - All rights reserved.
009     * @since 8/25/05
010     * @stereotype abstract state
011     */
012    abstract class ANode<T> {
013      /**
014       * Uses anonymous visitor class to compute a String representation.
015       */
016      private final IAlgo<T,String,Void> ToStringAlgo = new IAlgo<T,String,Void>() {
017        private final IAlgo<T,String,Void> Helper = new IAlgo<T,String,Void>() {
018          public String emptyCase(LRStruct<T> h, Void... i) {
019            return ")";
020          }
021          
022          public String nonEmptyCase(LRStruct<T> h, Void... i) {
023            return " " + h.getFirst() + h.getRest().execute (this);
024          }
025        };
026        
027        public String emptyCase(LRStruct<T> host, Void... inp) {
028          return "()";
029        }
030    
031        public String nonEmptyCase(LRStruct<T> host, Void... inp) {
032          return "(" + host.getFirst() + host.getRest().execute(Helper);
033        }
034      };
035      
036      String toString(LRStruct<T> owner) {
037        return (String)owner.execute (ToStringAlgo);
038      }
039      
040      /**
041       * Returns the tail LRStruct of the referencing LRStruct.
042       * @param owner the LRStruct referencing this ANode.
043       * @return the tail LRStruct of owner.
044       * @throw java.util.NoSuchElementException if empty.
045       */
046      abstract LRStruct<T> getRest(LRStruct<T> owner);
047      
048      /**
049       * Returns the first data object of the referencing LRStruct.
050       * @param owner the LRStruct referencing this ANode.
051       * @return the tail LRStruct of owner.
052       * @throw java.util.NoSuchElementException if empty.
053       */
054      abstract T getFirst(LRStruct<T> owner);
055      
056      /**
057       * Sets a new tail for the referencing LRStruct.
058       * @param tail the new tail for the owner LRStruct.
059       * @param owner the LRS referencing this ANode.
060       * @throw java.util.NoSuchElementException if empty.
061       * @return <code>LRStruct</code> owner
062       */
063      abstract LRStruct<T> setRest(LRStruct<T> tail, LRStruct<T> owner);
064      
065      /**
066       * Sets a new first data object for the referencing LRStruct.
067       * @param first the new data object for this ANode.
068       * @param owner the LRS referencing this ANode.
069       * @throw java.util.NoSuchElementException if empty.
070       * @return <code>LRStruct</code> owner
071       */
072      abstract LRStruct<T> setFirst(T dat, LRStruct<T> owner);
073      
074      /**
075       * Inserts a data object at the front of the LRStruct owner.
076       * @param dat the object to be inserted at the front.
077       * @param owner the LRS referencing this ANode.
078       * @return <code>LRStruct</code> owner
079       */
080      abstract LRStruct<T> insertFront(T dat, LRStruct<T> owner);
081      
082      /**
083       * Removes and returns the first data object for the referencing LRStruct.
084       * @param owner the LRS referencing this ANode.
085       * @return the front data of the LRStruct owner.
086       */
087      abstract T removeFront(LRStruct<T> owner);
088      
089      /**
090       * Executes a visitor algorithm and returns the output.
091       * @param owner the LRStruct referencing this ANode.
092       * @param algo the visitor algorithm to be executed.
093       * @param inp the inputs needed by the algorithm.
094       */
095      abstract <R,P> R execute(LRStruct<T> owner, IAlgo<T, R, P> algo, P ... inp);
096    }
097