View Javadoc

1   ////////////////////////////////////////////////////////////////////////////////
2   // MillScript: an Open Spice interpreter and batch website creation tool
3   // Copyright (C) 2001-2004 Open World Ltd
4   //
5   // This file is part of MillScript.
6   //
7   // MillScript is free software; you can redistribute it and/or modify it under
8   // the terms of the GNU General Public License as published by the Free
9   // Software Foundation; either version 2 of the License, or (at your option)
10  // any later version.
11  //
12  // MillScript is distributed in the hope that it will be useful, but WITHOUT
13  // ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
14  // FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
15  // more details.
16  //
17  // You should have received a copy of the GNU General Public License along with
18  // MillScript; if not, write to the Free Software Foundation, Inc., 59 Temple
19  // Place, Suite 330, Boston, MA  02111-1307  USA
20  ////////////////////////////////////////////////////////////////////////////////
21  package org.millscript.millscript.expr;
22  
23  import org.millscript.millscript.action.If3Action;
24  import org.millscript.millscript.vm.CompilerState;
25  
26  /**
27   * This class implements an if3 expression. An if3 expression has a predicate,
28   * ifso and ifnot expression, where if ifso expression is executed if the
29   * predicate expression returns <code>true</code> and the ifnot expression is
30   * executed otherwise.
31   *
32   * @see org.millscript.millscript.syntax.ConditionalSyntax
33   * @see If2Expr
34   * @see If3Action
35   */
36  public final class If3Expr extends Expr< If3Action > {
37  
38      /**
39       * Returns an if3 expression for the specified predicate, ifso and ifnot
40       * expressions. This method provides some compile-time optimisation,
41       * as it trys to simplify the predicate expression. If the predicate is a
42       * not expression, it remakes the if3 expression after removing the not.
43       *
44       * @param   a   the predicate expression which must return a single result
45       * @param   b   the ifso expression
46       * @param   c   the ifnot expression
47       * @return  an If3Expr for the specified values
48       */
49      public static Expr make( final Expr a, final Expr< ? > b, final Expr< ? > c ) {
50          // FIXME - When Sun fix their java compiler the method parameter can be
51          // made Expr< ? > and the suppress warnings can be removed
52          if ( a instanceof NotExpr ) {
53              return make( ((NotExpr) a).getCont(), c, b );
54          } else {
55              return new If3Expr( a, b, c );
56          }
57      }
58  
59      /**
60       * The ifnot expression, to be executed if the predicate returns
61       * <code>false</code>.
62       */
63      private final Expr< ? > ifnot;
64  
65      /**
66       * The ifso expression, to be executed if the predicate returns
67       * <code>true</code>.
68       */
69      private final Expr< ? > ifso;
70  
71      /**
72       * The predicate expression.
73       */
74      private final Expr< ? > pred;
75  
76      /**
77       * Creates a new if3 expression with the specified predicate, ifso and ifnot
78       * expressions.
79       *
80       * @param   a   the predicate expression which must return a single result
81       * @param   b   the ifso expression
82       * @param   c   the ifnot expression
83       */
84      public If3Expr( final Expr a, final Expr b, final Expr c ) {
85          pred = CheckExpr.make( a );
86          ifso = b;
87          ifnot = c;
88      }
89  
90      /**
91       * @see org.millscript.millscript.expr.Expr#arity()
92       */
93      @Override
94      public int arity() {
95          // An if3 expressions arity is only known if the ifso and ifnot
96          // expresssion have the same arity, otherwise it is unknown.
97          return joinArity( ifso.arity(), ifnot.arity() );
98      }
99  
100     /**
101      * @see org.millscript.millscript.expr.Expr#compileIt()
102      */
103     @Override
104     public If3Action compileIt() {
105         return new If3Action( pred.compile(), ifso.compile(), ifnot.compile() );
106     }
107 
108     /**
109      * @see org.millscript.millscript.expr.Expr#resolve(org.millscript.millscript.vm.CompilerState)
110      */
111     @Override
112     public void resolve( final CompilerState state ) {
113         this.pred.resolve( state );
114         this.ifso.resolve( state );
115         this.ifnot.resolve( state );
116     }
117 
118     /**
119      * @see org.millscript.millscript.expr.Expr#showComponents(int)
120      */
121     @Override
122     void showComponents( final int n ) {
123         this.pred.show( n );
124         this.ifso.show( n );
125         this.ifnot.show( n );
126     }
127 
128 }