mirror of git://gcc.gnu.org/git/gcc.git
				
				
				
			
		
			
				
	
	
		
			311 lines
		
	
	
		
			7.0 KiB
		
	
	
	
		
			Java
		
	
	
	
			
		
		
	
	
			311 lines
		
	
	
		
			7.0 KiB
		
	
	
	
		
			Java
		
	
	
	
// ChoiceFormat.java - Formatter for `switch'-like string substitution.
 | 
						|
 | 
						|
/* Copyright (C) 1999  Cygnus Solutions
 | 
						|
 | 
						|
   This file is part of libgcj.
 | 
						|
 | 
						|
This software is copyrighted work licensed under the terms of the
 | 
						|
Libgcj License.  Please consult the file "LIBGCJ_LICENSE" for
 | 
						|
details.  */
 | 
						|
 | 
						|
package java.text;
 | 
						|
 | 
						|
import java.util.Vector;
 | 
						|
 | 
						|
/**
 | 
						|
 * @author Tom Tromey <tromey@cygnus.com>
 | 
						|
 * @date March 9, 1999
 | 
						|
 */
 | 
						|
/* Written using "Java Class Libraries", 2nd edition, plus online
 | 
						|
 * API docs for JDK 1.2 from http://www.javasoft.com.
 | 
						|
 * Status:  Believed complete and correct to 1.1.
 | 
						|
 */
 | 
						|
 | 
						|
public class ChoiceFormat extends NumberFormat
 | 
						|
{
 | 
						|
  // Note: we assume the same kind of quoting rules apply here.
 | 
						|
  // This isn't explicitly documented.  But for instance we accept
 | 
						|
  // '#' as a literal hash in a format string.
 | 
						|
  public void applyPattern (String newPattern)
 | 
						|
    {
 | 
						|
      int index = 0, max = newPattern.length();
 | 
						|
      Vector stringVec = new Vector ();
 | 
						|
      Vector limitVec = new Vector ();
 | 
						|
      StringBuffer buf = new StringBuffer ();
 | 
						|
 | 
						|
      while (true)
 | 
						|
	{
 | 
						|
	  // Find end of double.
 | 
						|
	  int dstart = index;
 | 
						|
	  while (index < max)
 | 
						|
	    {
 | 
						|
	      char c = newPattern.charAt(index);
 | 
						|
	      if (c == '#' || c == '\u2064' || c == '<')
 | 
						|
		break;
 | 
						|
	      ++index;
 | 
						|
	    }
 | 
						|
 | 
						|
	  if (index == max)
 | 
						|
	    throw new IllegalArgumentException ("unexpected end of text");
 | 
						|
	  Double d = new Double (newPattern.substring(dstart, index));
 | 
						|
 | 
						|
	  if (newPattern.charAt(index) == '<')
 | 
						|
	    d = new Double (nextDouble (d.doubleValue()));
 | 
						|
 | 
						|
	  limitVec.addElement(d);
 | 
						|
 | 
						|
	  // Scan text.
 | 
						|
	  ++index;
 | 
						|
	  buf.setLength(0);
 | 
						|
	  while (index < max)
 | 
						|
	    {
 | 
						|
	      char c = newPattern.charAt(index);
 | 
						|
	      if (c == '\'' && index < max + 1
 | 
						|
		  && newPattern.charAt(index + 1) == '\'')
 | 
						|
		{
 | 
						|
		  buf.append(c);
 | 
						|
		  ++index;
 | 
						|
		}
 | 
						|
	      else if (c == '\'' && index < max + 2)
 | 
						|
		{
 | 
						|
		  buf.append(newPattern.charAt(index + 1));
 | 
						|
		  index += 2;
 | 
						|
		}
 | 
						|
	      else if (c == '|')
 | 
						|
		break;
 | 
						|
	      else
 | 
						|
		buf.append(c);
 | 
						|
	      ++index;
 | 
						|
	    }
 | 
						|
 | 
						|
	  stringVec.addElement(buf.toString());
 | 
						|
	  if (index == max)
 | 
						|
	    break;
 | 
						|
	  ++index;
 | 
						|
	}
 | 
						|
 | 
						|
      strings = new String[stringVec.size()];
 | 
						|
      stringVec.copyInto(strings);
 | 
						|
 | 
						|
      limits = new double[limitVec.size()];
 | 
						|
      for (int i = 0; i < limits.length; ++i)
 | 
						|
	{
 | 
						|
	  Double d = (Double) limitVec.elementAt(i);
 | 
						|
	  limits[i] = d.doubleValue();
 | 
						|
	}
 | 
						|
    }
 | 
						|
 | 
						|
  public ChoiceFormat (String newPattern)
 | 
						|
    {
 | 
						|
      super ();
 | 
						|
      applyPattern (newPattern);
 | 
						|
    }
 | 
						|
 | 
						|
  public ChoiceFormat (double[] limits, String[] strings)
 | 
						|
    {
 | 
						|
      super ();
 | 
						|
      setChoices (limits, strings);
 | 
						|
    }
 | 
						|
 | 
						|
  public Object clone ()
 | 
						|
    {
 | 
						|
      return new ChoiceFormat (limits, strings);
 | 
						|
    }
 | 
						|
 | 
						|
  public boolean equals (Object obj)
 | 
						|
    {
 | 
						|
      if (! (obj instanceof ChoiceFormat))
 | 
						|
	return false;
 | 
						|
      ChoiceFormat cf = (ChoiceFormat) obj;
 | 
						|
      if (limits.length != cf.limits.length)
 | 
						|
	return false;
 | 
						|
      for (int i = limits.length - 1; i >= 0; --i)
 | 
						|
	{
 | 
						|
	  if (limits[i] != cf.limits[i]
 | 
						|
	      || !strings[i].equals(cf.strings[i]))
 | 
						|
	    return false;
 | 
						|
	}
 | 
						|
      return true;
 | 
						|
    }
 | 
						|
 | 
						|
  public StringBuffer format (long num, StringBuffer appendBuf,
 | 
						|
			      FieldPosition pos)
 | 
						|
    {
 | 
						|
      return format ((double) num, appendBuf, pos);
 | 
						|
    }
 | 
						|
 | 
						|
  public StringBuffer format (double num, StringBuffer appendBuf,
 | 
						|
			      FieldPosition pos)
 | 
						|
    {
 | 
						|
      if (limits.length == 0)
 | 
						|
	return appendBuf;
 | 
						|
 | 
						|
      int index =  0;
 | 
						|
      if (! Double.isNaN(num) && num >= limits[0])
 | 
						|
	{
 | 
						|
	  for (; index < limits.length - 1; ++index)
 | 
						|
	    {
 | 
						|
	      if (limits[index] <= num
 | 
						|
		  && index != limits.length - 2
 | 
						|
		  && num < limits[index + 1])
 | 
						|
		break;
 | 
						|
	    }
 | 
						|
	}
 | 
						|
 | 
						|
      return appendBuf.append(strings[index]);
 | 
						|
    }
 | 
						|
 | 
						|
  public Object[] getFormats ()
 | 
						|
    {
 | 
						|
      return (Object[]) strings.clone();
 | 
						|
    }
 | 
						|
 | 
						|
  public double[] getLimits ()
 | 
						|
    {
 | 
						|
      return (double[]) limits.clone();
 | 
						|
    }
 | 
						|
 | 
						|
  public int hashCode ()
 | 
						|
    {
 | 
						|
      int hash = 0;
 | 
						|
      for (int i = 0; i < limits.length; ++i)
 | 
						|
	{
 | 
						|
	  long v = Double.doubleToLongBits(limits[i]);
 | 
						|
	  hash ^= (v ^ (v >>> 32));
 | 
						|
	  hash ^= strings[i].hashCode();
 | 
						|
	}
 | 
						|
      return hash;
 | 
						|
    }
 | 
						|
 | 
						|
  public static final double nextDouble (double d)
 | 
						|
    {
 | 
						|
      return nextDouble (d, true);
 | 
						|
    }
 | 
						|
 | 
						|
  public static final double nextDouble (double d, boolean next)
 | 
						|
    {
 | 
						|
      if (Double.isInfinite(d) || Double.isNaN(d))
 | 
						|
	return d;
 | 
						|
 | 
						|
      long bits = Double.doubleToLongBits(d);
 | 
						|
 | 
						|
      long mantMask = (1L << mantissaBits) - 1;
 | 
						|
      long mantissa = bits & mantMask;
 | 
						|
 | 
						|
      long expMask = (1L << exponentBits) - 1;
 | 
						|
      long exponent = (bits >>> mantissaBits) & expMask;
 | 
						|
 | 
						|
      if (next ^ (bits < 0)) // Increment magnitude
 | 
						|
	{
 | 
						|
	  if (mantissa == (1L << mantissaBits) - 1)
 | 
						|
	    {
 | 
						|
	      mantissa = 0L;
 | 
						|
	      exponent++;
 | 
						|
	     
 | 
						|
	      // Check for absolute overflow.
 | 
						|
	      if (exponent >= (1L << mantissaBits))
 | 
						|
		return (bits > 0) ? Double.POSITIVE_INFINITY 
 | 
						|
		  : Double.NEGATIVE_INFINITY;		      
 | 
						|
	    }
 | 
						|
	  else
 | 
						|
	    mantissa++;
 | 
						|
	}
 | 
						|
      else // Decrement magnitude
 | 
						|
	{
 | 
						|
	  if (exponent == 0L && mantissa == 0L)
 | 
						|
	    {
 | 
						|
	      // The only case where there is a change of sign
 | 
						|
	      return next ? Double.MIN_VALUE : -Double.MIN_VALUE;
 | 
						|
	    }
 | 
						|
	  else
 | 
						|
	    {
 | 
						|
	      if (mantissa == 0L)
 | 
						|
		{
 | 
						|
		  mantissa = (1L << mantissaBits) - 1;
 | 
						|
		  exponent--;
 | 
						|
		}
 | 
						|
	      else
 | 
						|
		mantissa--;
 | 
						|
	    }
 | 
						|
	}
 | 
						|
 | 
						|
      long result = bits < 0 ? 1 : 0;
 | 
						|
      result = (result << exponentBits) | exponent;
 | 
						|
      result = (result << mantissaBits) | mantissa;
 | 
						|
      return Double.longBitsToDouble(result);
 | 
						|
    }
 | 
						|
 | 
						|
  public Number parse (String sourceStr, ParsePosition pos)
 | 
						|
    {
 | 
						|
      int index = pos.getIndex();
 | 
						|
      for (int i = 0; i < limits.length; ++i)
 | 
						|
	{
 | 
						|
	  if (sourceStr.startsWith(strings[i], index))
 | 
						|
	    {
 | 
						|
	      pos.setIndex(index + strings[i].length());
 | 
						|
	      return new Double (limits[i]);
 | 
						|
	    }
 | 
						|
	}
 | 
						|
      pos.setErrorIndex(index);
 | 
						|
      return new Double (Double.NaN);
 | 
						|
    }
 | 
						|
 | 
						|
  public static final double previousDouble (double d)
 | 
						|
    {
 | 
						|
      return nextDouble (d, false);
 | 
						|
    }
 | 
						|
 | 
						|
  public void setChoices (double[] limits, String[] strings)
 | 
						|
    {
 | 
						|
      if (limits == null || strings == null)
 | 
						|
	throw new NullPointerException ();
 | 
						|
      if (limits.length != strings.length)
 | 
						|
	throw new IllegalArgumentException ();
 | 
						|
      this.strings = (String[]) strings.clone();
 | 
						|
      this.limits = (double[]) limits.clone();
 | 
						|
    }
 | 
						|
 | 
						|
  private final void quoteString (StringBuffer dest, String text)
 | 
						|
    {
 | 
						|
      int max = text.length();
 | 
						|
      for (int i = 0; i < max; ++i)
 | 
						|
	{
 | 
						|
	  char c = text.charAt(i);
 | 
						|
	  if (c == '\'')
 | 
						|
	    {
 | 
						|
	      dest.append(c);
 | 
						|
	      dest.append(c);
 | 
						|
	    }
 | 
						|
	  else if (c == '#' || c == '|' || c == '\u2064' || c == '<')
 | 
						|
	    {
 | 
						|
	      dest.append('\'');
 | 
						|
	      dest.append(c);
 | 
						|
	      dest.append('\'');
 | 
						|
	    }
 | 
						|
	  else
 | 
						|
	    dest.append(c);
 | 
						|
	}
 | 
						|
    }
 | 
						|
 | 
						|
  public String toPattern ()
 | 
						|
    {
 | 
						|
      StringBuffer result = new StringBuffer ();
 | 
						|
      for (int i = 0; i < limits.length; ++i)
 | 
						|
	{
 | 
						|
	  result.append(limits[i]);
 | 
						|
	  result.append('#');
 | 
						|
	  quoteString (result, strings[i]);
 | 
						|
	}
 | 
						|
      return result.toString();
 | 
						|
    }
 | 
						|
 | 
						|
  // Formats and limits.
 | 
						|
  private String[] strings;
 | 
						|
  private double[] limits;
 | 
						|
 | 
						|
  // Number of mantissa bits in double.
 | 
						|
  private static final int mantissaBits = 52;
 | 
						|
  // Number of exponent bits in a double.
 | 
						|
  private static final int exponentBits = 11;
 | 
						|
}
 |