001/*
002 * Units of Measurement Reference Implementation
003 * Copyright (c) 2005-2017, Jean-Marie Dautelle, Werner Keil, V2COM.
004 *
005 * All rights reserved.
006 *
007 * Redistribution and use in source and binary forms, with or without modification,
008 * are permitted provided that the following conditions are met:
009 *
010 * 1. Redistributions of source code must retain the above copyright notice,
011 *    this list of conditions and the following disclaimer.
012 *
013 * 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions
014 *    and the following disclaimer in the documentation and/or other materials provided with the distribution.
015 *
016 * 3. Neither the name of JSR-363 nor the names of its contributors may be used to endorse or promote products
017 *    derived from this software without specific prior written permission.
018 *
019 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
020 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
021 * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
022 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
023 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
024 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
025 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
026 * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
027 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
028 * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
029 */
030package tec.units.ri.unit;
031
032import static tec.units.ri.internal.MathUtil.pow;
033
034import javax.measure.Quantity;
035import javax.measure.Unit;
036import javax.measure.UnitConverter;
037
038import tec.units.ri.function.RationalConverter;
039import tec.uom.lib.common.function.SymbolSupplier;
040import tec.uom.lib.common.function.UnitConverterSupplier;
041
042/**
043 * <p>
044 * This class provides support for the 20 prefixes used in the metric system (decimal multiples and submultiples of units). For example:
045 * 
046 * <pre>
047 * <code>
048 *     import static tec.units.ri.unit.Units.*;  // Static import.
049 *     import static tec.units.ri.unit.MetricPrefix.*; // Static import.
050 *     import javax.measure.*;
051 *     import javax.measure.quantity.*;
052 *     ...
053 *     Unit<Pressure> HECTOPASCAL = HECTO(PASCAL);
054 *     Unit<Length> KILOMETRE = KILO(METRE);
055 *     </code>
056 * </pre>
057 * 
058 * </p>
059 *
060 * @see <a href="http://en.wikipedia.org/wiki/Metric_prefix">Wikipedia: Metric Prefix</a>
061 * @author <a href="mailto:jean-marie@dautelle.com">Jean-Marie Dautelle</a>
062 * @author <a href="mailto:units@catmedia.us">Werner Keil</a>
063 * @version 1.0, $Date: 2016-10-06 $
064 * @since 1.0
065 */
066public enum MetricPrefix implements SymbolSupplier, UnitConverterSupplier {
067  YOTTA("Y", RationalConverter.of(1000000000000000000000000d, 1d)), ZETTA("Z", RationalConverter.of(1000000000000000000000d, 1d)), EXA("E",
068      RationalConverter.of(pow(10, 18), 1d)), PETA("P", RationalConverter.of(pow(10, 15), 1d)), TERA("T", RationalConverter.of(pow(10, 12), 1d)), GIGA(
069      "G", RationalConverter.of(pow(10, 9), 1d)), MEGA("M", RationalConverter.of(pow(10, 6), 1d)), KILO("k", RationalConverter.of(pow(10, 3), 1d)), HECTO(
070      "h", RationalConverter.of(100d, 1d)), DEKA("da", RationalConverter.of(10d, 1d)), DECI("d", RationalConverter.of(1d, 10d)), CENTI("c",
071      RationalConverter.of(1d, 100d)), MILLI("m", RationalConverter.of(1d, 1000d)), MICRO("µ", RationalConverter.of(1d, pow(10, 6))), NANO("n",
072      RationalConverter.of(1d, pow(10, 9))), PICO("p", RationalConverter.of(1d, pow(10, 12))), FEMTO("f", RationalConverter.of(1d, pow(10, 15))), ATTO(
073      "a", RationalConverter.of(1d, pow(10, 18))), ZEPTO("z", RationalConverter.of(1d, pow(10, 21))), YOCTO("y", RationalConverter
074      .of(1d, pow(10, 24)));
075
076  /**
077   * The symbol of this prefix, as returned by {@link #getSymbol}.
078   *
079   * @serial
080   * @see #getSymbol()
081   */
082  private final String symbol;
083
084  /**
085   * The <code>UnitConverter</code> of this prefix, as returned by {@link #getConverter}.
086   *
087   * @serial
088   * @see #getConverter()
089   * @see {@link UnitConverter}
090   */
091  private final UnitConverter converter;
092
093  /**
094   * Creates a new prefix.
095   *
096   * @param symbol
097   *          the symbol of this prefix.
098   * @param converter
099   *          the associated unit converter.
100   */
101  MetricPrefix(String symbol, RationalConverter converter) {
102    this.symbol = symbol;
103    this.converter = converter;
104  }
105
106  /**
107   * Returns the symbol of this prefix.
108   *
109   * @return this prefix symbol, not {@code null}.
110   * 
111   * @see #toString()
112   */
113  public String getSymbol() {
114    return symbol;
115  }
116
117  /**
118   * Returns the corresponding unit converter.
119   *
120   * @return the unit converter.
121   */
122  public UnitConverter getConverter() {
123    return converter;
124  }
125
126  /**
127   * Returns the specified unit multiplied by the factor <code>10<sup>24</sup></code>
128   *
129   * @param <Q>
130   *          The type of the quantity measured by the unit.
131   * @param unit
132   *          any unit.
133   * @return <code>unit.multiply(1e24)</code>.
134   */
135  public static final <Q extends Quantity<Q>> Unit<Q> YOTTA(Unit<Q> unit) {
136    return unit.transform(YOTTA.getConverter());
137  }
138
139  /**
140   * Returns the specified unit multiplied by the factor <code>10<sup>21</sup></code>
141   *
142   * @param <Q>
143   *          The type of the quantity measured by the unit.
144   * @param unit
145   *          any unit.
146   * @return <code>unit.multiply(1e21)</code>.
147   */
148  public static final <Q extends Quantity<Q>> Unit<Q> ZETTA(Unit<Q> unit) {
149    return unit.transform(ZETTA.getConverter());
150  }
151
152  /**
153   * Returns the specified unit multiplied by the factor <code>10<sup>18</sup></code>
154   *
155   * @param <Q>
156   *          The type of the quantity measured by the unit.
157   * @param unit
158   *          any unit.
159   * @return <code>unit.multiply(1e18)</code>.
160   */
161  public static final <Q extends Quantity<Q>> Unit<Q> EXA(Unit<Q> unit) {
162    return unit.transform(EXA.getConverter());
163  }
164
165  /**
166   * Returns the specified unit multiplied by the factor <code>10<sup>15</sup></code>
167   *
168   * @param <Q>
169   *          The type of the quantity measured by the unit.
170   * @param unit
171   *          any unit.
172   * @return <code>unit.multiply(1e15)</code>.
173   */
174  public static final <Q extends Quantity<Q>> Unit<Q> PETA(Unit<Q> unit) {
175    return unit.transform(PETA.getConverter());
176  }
177
178  /**
179   * Returns the specified unit multiplied by the factor <code>10<sup>12</sup></code>
180   *
181   * @param <Q>
182   *          The type of the quantity measured by the unit.
183   * @param unit
184   *          any unit.
185   * @return <code>unit.multiply(1e12)</code>.
186   */
187  public static final <Q extends Quantity<Q>> Unit<Q> TERA(Unit<Q> unit) {
188    return unit.transform(TERA.getConverter());
189  }
190
191  /**
192   * Returns the specified unit multiplied by the factor <code>10<sup>9</sup></code>
193   *
194   * @param <Q>
195   *          The type of the quantity measured by the unit.
196   * @param unit
197   *          any unit.
198   * @return <code>unit.multiply(1e9)</code>.
199   */
200  public static <Q extends Quantity<Q>> Unit<Q> GIGA(Unit<Q> unit) {
201    return unit.transform(GIGA.getConverter());
202  }
203
204  /**
205   * Returns the specified unit multiplied by the factor <code>10<sup>6</sup></code>
206   *
207   * @param <Q>
208   *          The type of the quantity measured by the unit.
209   * @param unit
210   *          any unit.
211   * @return <code>unit.multiply(1e6)</code>.
212   */
213  public static final <Q extends Quantity<Q>> Unit<Q> MEGA(Unit<Q> unit) {
214    return unit.transform(MEGA.getConverter());
215  }
216
217  /**
218   * Returns the specified unit multiplied by the factor <code>10<sup>3</sup></code>
219   *
220   * @param <Q>
221   *          The type of the quantity measured by the unit.
222   * @param unit
223   *          any unit.
224   * @return <code>unit.multiply(1e3)</code>.
225   */
226  public static final <Q extends Quantity<Q>> Unit<Q> KILO(Unit<Q> unit) {
227    return unit.transform(KILO.getConverter());
228  }
229
230  /**
231   * Returns the specified unit multiplied by the factor <code>10<sup>2</sup></code>
232   *
233   * @param <Q>
234   *          The type of the quantity measured by the unit.
235   * @param unit
236   *          any unit.
237   * @return <code>unit.multiply(1e2)</code>.
238   */
239  public static final <Q extends Quantity<Q>> Unit<Q> HECTO(Unit<Q> unit) {
240    return unit.transform(HECTO.getConverter());
241  }
242
243  /**
244   * Returns the specified unit multiplied by the factor <code>10<sup>1</sup></code>
245   *
246   * @param <Q>
247   *          The type of the quantity measured by the unit.
248   * @param unit
249   *          any unit.
250   * @return <code>unit.multiply(1e1)</code>.
251   */
252  public static final <Q extends Quantity<Q>> Unit<Q> DEKA(Unit<Q> unit) {
253    return unit.transform(DEKA.getConverter());
254  }
255
256  /**
257   * Returns the specified unit multiplied by the factor <code>10<sup>-1</sup></code>
258   *
259   * @param <Q>
260   *          The type of the quantity measured by the unit.
261   * @param unit
262   *          any unit.
263   * @return <code>unit.multiply(1e-1)</code>.
264   */
265  public static final <Q extends Quantity<Q>> Unit<Q> DECI(Unit<Q> unit) {
266    return unit.transform(DECI.getConverter());
267  }
268
269  /**
270   * Returns the specified unit multiplied by the factor <code>10<sup>-2</sup></code>
271   *
272   * @param <Q>
273   *          The type of the quantity measured by the unit.
274   * @param unit
275   *          any unit.
276   * @return <code>unit.multiply(1e-2)</code>.
277   */
278  public static <Q extends Quantity<Q>> Unit<Q> CENTI(Unit<Q> unit) {
279    return unit.transform(CENTI.getConverter());
280  }
281
282  /**
283   * Returns the specified unit multiplied by the factor <code>10<sup>-3</sup></code>
284   *
285   * @param <Q>
286   *          The type of the quantity measured by the unit.
287   * @param unit
288   *          any unit.
289   * @return <code>unit.multiply(1e-3)</code>.
290   */
291  public static final <Q extends Quantity<Q>> Unit<Q> MILLI(Unit<Q> unit) {
292    return unit.transform(MILLI.getConverter());
293  }
294
295  /**
296   * Returns the specified unit multiplied by the factor <code>10<sup>-6</sup></code>
297   *
298   * @param <Q>
299   *          The type of the quantity measured by the unit.
300   * @param unit
301   *          any unit.
302   * @return <code>unit.multiply(1e-6)</code>.
303   */
304  public static final <Q extends Quantity<Q>> Unit<Q> MICRO(Unit<Q> unit) {
305    return unit.transform(MICRO.getConverter());
306  }
307
308  /**
309   * Returns the specified unit multiplied by the factor <code>10<sup>-9</sup></code>
310   *
311   * @param <Q>
312   *          The type of the quantity measured by the unit.
313   * @param unit
314   *          any unit.
315   * @return <code>unit.multiply(1e-9)</code>.
316   */
317  public static final <Q extends Quantity<Q>> Unit<Q> NANO(Unit<Q> unit) {
318    return unit.transform(NANO.getConverter());
319  }
320
321  /**
322   * Returns the specified unit multiplied by the factor <code>10<sup>-12</sup></code>
323   *
324   * @param <Q>
325   *          The type of the quantity measured by the unit.
326   * @param unit
327   *          any unit.
328   * @return <code>unit.multiply(1e-12)</code>.
329   */
330  public static final <Q extends Quantity<Q>> Unit<Q> PICO(Unit<Q> unit) {
331    return unit.transform(PICO.getConverter());
332  }
333
334  /**
335   * Returns the specified unit multiplied by the factor <code>10<sup>-15</sup></code>
336   *
337   * @param <Q>
338   *          The type of the quantity measured by the unit.
339   * @param unit
340   *          any unit.
341   * @return <code>unit.multiply(1e-15)</code>.
342   */
343  public static final <Q extends Quantity<Q>> Unit<Q> FEMTO(Unit<Q> unit) {
344    return unit.transform(FEMTO.getConverter());
345  }
346
347  /**
348   * Returns the specified unit multiplied by the factor <code>10<sup>-18</sup></code>
349   *
350   * @param <Q>
351   *          The type of the quantity measured by the unit.
352   * @param unit
353   *          any unit.
354   * @return <code>unit.multiply(1e-18)</code>.
355   */
356  public static final <Q extends Quantity<Q>> Unit<Q> ATTO(Unit<Q> unit) {
357    return unit.transform(ATTO.getConverter());
358  }
359
360  /**
361   * Returns the specified unit multiplied by the factor <code>10<sup>-21</sup></code>
362   *
363   * @param <Q>
364   *          The type of the quantity measured by the unit.
365   * @param unit
366   *          any unit.
367   * @return <code>unit.multiply(1e-21)</code>.
368   */
369  public static final <Q extends Quantity<Q>> Unit<Q> ZEPTO(Unit<Q> unit) {
370    return unit.transform(ZEPTO.getConverter());
371  }
372
373  /**
374   * Returns the specified unit multiplied by the factor <code>10<sup>-24</sup></code>
375   *
376   * @param <Q>
377   *          The type of the quantity measured by the unit.
378   * @param unit
379   *          any unit.
380   * @return <code>unit.multiply(1e-24)</code>.
381   */
382  public static final <Q extends Quantity<Q>> Unit<Q> YOCTO(Unit<Q> unit) {
383    return unit.transform(YOCTO.getConverter());
384  }
385}