    001/*
    002 * Licensed to the Apache Software Foundation (ASF) under one or more
    003 * contributor license agreements.  See the NOTICE file distributed with
    004 * this work for additional information regarding copyright ownership.
    005 * The ASF licenses this file to You under the Apache License, Version 2.0
    006 * (the "License"); you may not use this file except in compliance with
    007 * the License.  You may obtain a copy of the License at
    008 *
    009 *      http://www.apache.org/licenses/LICENSE-2.0
    010 *
    011 * Unless required by applicable law or agreed to in writing, software
    012 * distributed under the License is distributed on an "AS IS" BASIS,
    013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    014 * See the License for the specific language governing permissions and
    015 * limitations under the License.
    016 */
    017package org.apache.commons.lang3.mutable;
    018
    019/**
    020 * A mutable {@code double} wrapper.
    021 * <p>
    022 * Note that as MutableDouble does not extend Double, it is not treated by String.format as a Double parameter.
    023 * </p>
    024 *
    025 * @see Double
    026 * @since 2.1
    027 */
    028public class MutableDouble extends Number implements Comparable<MutableDouble>, Mutable<Number> {
    029
    030    /**
    031     * Required for serialization support.
    032     *
    033     * @see java.io.Serializable
    034     */
    035    private static final long serialVersionUID = 1587163916L;
    036
    037    /** The mutable value. */
    038    private double value;
    039
    040    /**
    041     * Constructs a new MutableDouble with the default value of zero.
    042     */
    043    public MutableDouble() {
    044    }
    045
    046    /**
    047     * Constructs a new MutableDouble with the specified value.
    048     *
    049     * @param value  the initial value to store
    050     */
    051    public MutableDouble(final double value) {
    052        this.value = value;
    053    }
    054
    055    /**
    056     * Constructs a new MutableDouble with the specified value.
    057     *
    058     * @param value  the initial value to store, not null
    059     * @throws NullPointerException if the object is null
    060     */
    061    public MutableDouble(final Number value) {
    062        this.value = value.doubleValue();
    063    }
    064
    065    /**
    066     * Constructs a new MutableDouble parsing the given string.
    067     *
    068     * @param value  the string to parse, not null
    069     * @throws NumberFormatException if the string cannot be parsed into a double
    070     * @since 2.5
    071     */
    072    public MutableDouble(final String value) {
    073        this.value = Double.parseDouble(value);
    074    }
    075
    076    /**
    077     * Gets the value as a Double instance.
    078     *
    079     * @return the value as a Double, never null
    080     */
    081    @Override
    082    public Double getValue() {
    083        return Double.valueOf(this.value);
    084    }
    085
    086    /**
    087     * Sets the value.
    088     *
    089     * @param value  the value to set
    090     */
    091    public void setValue(final double value) {
    092        this.value = value;
    093    }
    094
    095    /**
    096     * Sets the value from any Number instance.
    097     *
    098     * @param value  the value to set, not null
    099     * @throws NullPointerException if the object is null
    100     */
    101    @Override
    102    public void setValue(final Number value) {
    103        this.value = value.doubleValue();
    104    }
    105
    106    /**
    107     * Checks whether the double value is the special NaN value.
    108     *
    109     * @return true if NaN
    110     */
    111    public boolean isNaN() {
    112        return Double.isNaN(value);
    113    }
    114
    115    /**
    116     * Checks whether the double value is infinite.
    117     *
    118     * @return true if infinite
    119     */
    120    public boolean isInfinite() {
    121        return Double.isInfinite(value);
    122    }
    123
    124    /**
    125     * Increments the value.
    126     *
    127     * @since 2.2
    128     */
    129    public void increment() {
    130        value++;
    131    }
    132
    133    /**
    134     * Increments this instance's value by 1; this method returns the value associated with the instance
    135     * immediately prior to the increment operation. This method is not thread safe.
    136     *
    137     * @return the value associated with the instance before it was incremented
    138     * @since 3.5
    139     */
    140    public double getAndIncrement() {
    141        final double last = value;
    142        value++;
    143        return last;
    144    }
    145
    146    /**
    147     * Increments this instance's value by 1; this method returns the value associated with the instance
    148     * immediately after the increment operation. This method is not thread safe.
    149     *
    150     * @return the value associated with the instance after it is incremented
    151     * @since 3.5
    152     */
    153    public double incrementAndGet() {
    154        value++;
    155        return value;
    156    }
    157
    158    /**
    159     * Decrements the value.
    160     *
    161     * @since 2.2
    162     */
    163    public void decrement() {
    164        value--;
    165    }
    166
    167    /**
    168     * Decrements this instance's value by 1; this method returns the value associated with the instance
    169     * immediately prior to the decrement operation. This method is not thread safe.
    170     *
    171     * @return the value associated with the instance before it was decremented
    172     * @since 3.5
    173     */
    174    public double getAndDecrement() {
    175        final double last = value;
    176        value--;
    177        return last;
    178    }
    179
    180    /**
    181     * Decrements this instance's value by 1; this method returns the value associated with the instance
    182     * immediately after the decrement operation. This method is not thread safe.
    183     *
    184     * @return the value associated with the instance after it is decremented
    185     * @since 3.5
    186     */
    187    public double decrementAndGet() {
    188        value--;
    189        return value;
    190    }
    191
    192    /**
    193     * Adds a value to the value of this instance.
    194     *
    195     * @param operand  the value to add
    196     * @since 2.2
    197     */
    198    public void add(final double operand) {
    199        this.value += operand;
    200    }
    201
    202    /**
    203     * Adds a value to the value of this instance.
    204     *
    205     * @param operand  the value to add, not null
    206     * @throws NullPointerException if the object is null
    207     * @since 2.2
    208     */
    209    public void add(final Number operand) {
    210        this.value += operand.doubleValue();
    211    }
    212
    213    /**
    214     * Subtracts a value from the value of this instance.
    215     *
    216     * @param operand  the value to subtract, not null
    217     * @since 2.2
    218     */
    219    public void subtract(final double operand) {
    220        this.value -= operand;
    221    }
    222
    223    /**
    224     * Subtracts a value from the value of this instance.
    225     *
    226     * @param operand  the value to subtract, not null
    227     * @throws NullPointerException if the object is null
    228     * @since 2.2
    229     */
    230    public void subtract(final Number operand) {
    231        this.value -= operand.doubleValue();
    232    }
    233
    234    /**
    235     * Increments this instance's value by {@code operand}; this method returns the value associated with the instance
    236     * immediately after the addition operation. This method is not thread safe.
    237     *
    238     * @param operand the quantity to add, not null
    239     * @return the value associated with this instance after adding the operand
    240     * @since 3.5
    241     */
    242    public double addAndGet(final double operand) {
    243        this.value += operand;
    244        return value;
    245    }
    246
    247    /**
    248     * Increments this instance's value by {@code operand}; this method returns the value associated with the instance
    249     * immediately after the addition operation. This method is not thread safe.
    250     *
    251     * @param operand the quantity to add, not null
    252     * @throws NullPointerException if {@code operand} is null
    253     * @return the value associated with this instance after adding the operand
    254     * @since 3.5
    255     */
    256    public double addAndGet(final Number operand) {
    257        this.value += operand.doubleValue();
    258        return value;
    259    }
    260
    261    /**
    262     * Increments this instance's value by {@code operand}; this method returns the value associated with the instance
    263     * immediately prior to the addition operation. This method is not thread safe.
    264     *
    265     * @param operand the quantity to add, not null
    266     * @return the value associated with this instance immediately before the operand was added
    267     * @since 3.5
    268     */
    269    public double getAndAdd(final double operand) {
    270        final double last = value;
    271        this.value += operand;
    272        return last;
    273    }
    274
    275    /**
    276     * Increments this instance's value by {@code operand}; this method returns the value associated with the instance
    277     * immediately prior to the addition operation. This method is not thread safe.
    278     *
    279     * @param operand the quantity to add, not null
    280     * @throws NullPointerException if {@code operand} is null
    281     * @return the value associated with this instance immediately before the operand was added
    282     * @since 3.5
    283     */
    284    public double getAndAdd(final Number operand) {
    285        final double last = value;
    286        this.value += operand.doubleValue();
    287        return last;
    288    }
    289
    290    // shortValue and byteValue rely on Number implementation
    291    /**
    292     * Returns the value of this MutableDouble as an int.
    293     *
    294     * @return the numeric value represented by this object after conversion to type int.
    295     */
    296    @Override
    297    public int intValue() {
    298        return (int) value;
    299    }
    300
    301    /**
    302     * Returns the value of this MutableDouble as a long.
    303     *
    304     * @return the numeric value represented by this object after conversion to type long.
    305     */
    306    @Override
    307    public long longValue() {
    308        return (long) value;
    309    }
    310
    311    /**
    312     * Returns the value of this MutableDouble as a float.
    313     *
    314     * @return the numeric value represented by this object after conversion to type float.
    315     */
    316    @Override
    317    public float floatValue() {
    318        return (float) value;
    319    }
    320
    321    /**
    322     * Returns the value of this MutableDouble as a double.
    323     *
    324     * @return the numeric value represented by this object after conversion to type double.
    325     */
    326    @Override
    327    public double doubleValue() {
    328        return value;
    329    }
    330
    331    /**
    332     * Gets this mutable as an instance of Double.
    333     *
    334     * @return a Double instance containing the value from this mutable, never null
    335     */
    336    public Double toDouble() {
    337        return Double.valueOf(doubleValue());
    338    }
    339
    340    /**
    341     * Compares this object against the specified object. The result is {@code true} if and only if the argument
    342     * is not {@code null} and is a {@link Double} object that represents a double that has the identical
    343     * bit pattern to the bit pattern of the double represented by this object. For this purpose, two
    344     * {@code double} values are considered to be the same if and only if the method
    345     * {@link Double#doubleToLongBits(double)}returns the same long value when applied to each.
    346     * <p>
    347     * Note that in most cases, for two instances of class {@link Double},{@code d1} and {@code d2},
    348     * the value of {@code d1.equals(d2)} is {@code true} if and only if <blockquote>
    349     *
    350     * <pre>
    351     *   d1.doubleValue()&nbsp;== d2.doubleValue()
    352     * </pre>
    353     *
    354     * </blockquote>
    355     * <p>
    356     * also has the value {@code true}. However, there are two exceptions:
    357     * <ul>
    358     * <li>If {@code d1} and {@code d2} both represent {@code Double.NaN}, then the
    359     * {@code equals} method returns {@code true}, even though {@code Double.NaN==Double.NaN} has
    360     * the value {@code false}.
    361     * <li>If {@code d1} represents {@code +0.0} while {@code d2} represents {@code -0.0},
    362     * or vice versa, the {@code equal} test has the value {@code false}, even though
    363     * {@code +0.0==-0.0} has the value {@code true}. This allows hashtables to operate properly.
    364     * </ul>
    365     *
    366     * @param obj  the object to compare with, null returns false
    367     * @return {@code true} if the objects are the same; {@code false} otherwise.
    368     */
    369    @Override
    370    public boolean equals(final Object obj) {
    371        return obj instanceof MutableDouble
    372            && Double.doubleToLongBits(((MutableDouble) obj).value) == Double.doubleToLongBits(value);
    373    }
    374
    375    /**
    376     * Returns a suitable hash code for this mutable.
    377     *
    378     * @return a suitable hash code
    379     */
    380    @Override
    381    public int hashCode() {
    382        final long bits = Double.doubleToLongBits(value);
    383        return (int) (bits ^ bits >>> 32);
    384    }
    385
    386    /**
    387     * Compares this mutable to another in ascending order.
    388     *
    389     * @param other  the other mutable to compare to, not null
    390     * @return negative if this is less, zero if equal, positive if greater
    391     */
    392    @Override
    393    public int compareTo(final MutableDouble other) {
    394        return Double.compare(this.value, other.value);
    395    }
    396
    397    /**
    398     * Returns the String value of this mutable.
    399     *
    400     * @return the mutable value as a string
    401     */
    402    @Override
    403    public String toString() {
    404        return String.valueOf(value);
    405    }
    406
    407}