View Javadoc

1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one or more
3    * contributor license agreements.  See the NOTICE file distributed with
4    * this work for additional information regarding copyright ownership.
5    * The ASF licenses this file to You under the Apache License, Version 2.0
6    * (the "License"); you may not use this file except in compliance with
7    * the License.  You may obtain a copy of the License at
8    *
9    *     http://www.apache.org/licenses/LICENSE-2.0
10   *
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS,
13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14   * See the License for the specific language governing permissions and
15   * limitations under the License.
16   */
17  package org.apache.commons.el;
18  
19  import java.math.BigInteger;
20  
21  import javax.servlet.jsp.el.ELException;
22  
23  import org.apache.commons.logging.Log;
24  import org.apache.commons.logging.LogFactory;
25  
26  /**
27   *
28   * <p>The implementation of the modulus operator
29   * 
30   * @author Nathan Abramson - Art Technology Group
31   * @version $Change: 181177 $$DateTime: 2001/06/26 08:45:09 $$Author: bayard $
32   **/
33  
34  public class ModulusOperator
35    extends BinaryOperator
36  {
37      
38      //-------------------------------------
39      // Constants
40      //-------------------------------------
41      private static Log log = LogFactory.getLog(ModulusOperator.class);
42      
43    //-------------------------------------
44    // Singleton
45    //-------------------------------------
46  
47    public static final ModulusOperator SINGLETON =
48      new ModulusOperator ();
49  
50    //-------------------------------------
51    /**
52     *
53     * Constructor
54     **/
55    public ModulusOperator ()
56    {
57    }
58  
59    //-------------------------------------
60    // Expression methods
61    //-------------------------------------
62    /**
63     *
64     * Returns the symbol representing the operator
65     **/
66    public String getOperatorSymbol ()
67    {
68      return "%";
69    }
70  
71    //-------------------------------------
72    /**
73     *
74     * Applies the operator to the given value
75     **/
76    public Object apply (Object pLeft, Object pRight)
77      throws ELException
78    {
79      if (pLeft == null &&
80  	pRight == null) {
81          if (log.isWarnEnabled()) {
82              log.warn(
83                  MessageUtil.getMessageWithArgs(
84                      Constants.ARITH_OP_NULL, getOperatorSymbol()));
85          }     
86        return PrimitiveObjects.getInteger (0);
87      }
88  
89      if ((pLeft != null &&
90  	 (Coercions.isFloatingPointType (pLeft) ||
91  	  Coercions.isFloatingPointString (pLeft))) ||
92        Coercions.isBigDecimal(pLeft) ||
93  	(pRight != null &&
94  	 (Coercions.isFloatingPointType (pRight) ||
95  	  Coercions.isFloatingPointString (pRight) ||
96        Coercions.isBigDecimal(pRight)))) {
97        double left =
98  	Coercions.coerceToPrimitiveNumber (pLeft, Double.class).
99  	doubleValue ();
100       double right =
101 	Coercions.coerceToPrimitiveNumber (pRight, Double.class).
102 	doubleValue ();
103 
104       try {
105 	return PrimitiveObjects.getDouble (left % right);
106       }
107       catch (Exception exc) {
108           if (log.isErrorEnabled()) {
109               String message = MessageUtil.getMessageWithArgs(
110                   Constants.ARITH_ERROR,
111                   getOperatorSymbol(),
112                   "" + left,
113                   "" + right);
114               log.error(message);
115               throw new ELException(message);
116           }	
117 	return PrimitiveObjects.getInteger (0);
118       }
119     }
120     else if (Coercions.isBigInteger(pLeft) || Coercions.isBigInteger(pRight)) {
121         BigInteger left = (BigInteger)
122              Coercions.coerceToPrimitiveNumber(pLeft, BigInteger.class);
123         BigInteger right = (BigInteger)
124             Coercions.coerceToPrimitiveNumber(pRight, BigInteger.class);
125 
126         try {
127             return left.remainder(right);
128         } catch (Exception exc) {
129             if (log.isErrorEnabled()) {
130                 String message = MessageUtil.getMessageWithArgs(
131                     Constants.ARITH_ERROR,
132                     getOperatorSymbol(),
133                     "" + left,
134                     "" + right);
135                 log.error(message);
136                 throw new ELException(message);
137             }	           
138             return PrimitiveObjects.getInteger(0);
139         }
140     }
141     else {
142       long left =
143 	Coercions.coerceToPrimitiveNumber (pLeft, Long.class).
144 	longValue ();
145       long right =
146 	Coercions.coerceToPrimitiveNumber (pRight, Long.class).
147 	longValue ();
148 
149       try {
150 	return PrimitiveObjects.getLong (left % right);
151       }
152       catch (Exception exc) {
153           if (log.isErrorEnabled()) {
154               String message = MessageUtil.getMessageWithArgs(
155                   Constants.ARITH_ERROR,
156                   getOperatorSymbol(),
157                   "" + left,
158                   "" + right);
159               log.error(message);
160               throw new ELException(message);
161           }		
162 	return PrimitiveObjects.getInteger (0);
163       }
164     }
165   }
166 
167   //-------------------------------------
168 }