2017-07-25 13:58:09 -07:00
|
|
|
package org.nwapw.abacus.number;
|
|
|
|
|
2017-07-25 22:47:48 -07:00
|
|
|
/**
|
|
|
|
* An interface used to represent a number.
|
|
|
|
*/
|
2017-08-05 13:54:06 -07:00
|
|
|
public abstract class NumberInterface {
|
2017-07-25 13:58:09 -07:00
|
|
|
|
2017-08-05 13:54:06 -07:00
|
|
|
/**
|
|
|
|
* Check if the thread was interrupted and
|
|
|
|
* throw an exception to end the computation.
|
|
|
|
*/
|
|
|
|
private static void checkInterrupted(){
|
|
|
|
if(Thread.currentThread().isInterrupted())
|
|
|
|
throw new ComputationInterruptedException();
|
|
|
|
}
|
2017-07-25 22:47:48 -07:00
|
|
|
/**
|
2017-07-28 20:04:13 -07:00
|
|
|
* The maximum precision to which this number operates.
|
2017-07-30 21:11:32 -07:00
|
|
|
*
|
2017-07-25 22:47:48 -07:00
|
|
|
* @return the precision.
|
|
|
|
*/
|
2017-08-05 13:54:06 -07:00
|
|
|
public abstract int getMaxPrecision();
|
2017-07-25 22:47:48 -07:00
|
|
|
|
|
|
|
/**
|
|
|
|
* Multiplies this number by another, returning
|
|
|
|
* a new number instance.
|
2017-07-30 21:11:32 -07:00
|
|
|
*
|
2017-07-25 22:47:48 -07:00
|
|
|
* @param multiplier the multiplier
|
|
|
|
* @return the result of the multiplication.
|
|
|
|
*/
|
2017-08-05 13:54:06 -07:00
|
|
|
protected abstract NumberInterface multiplyInternal(NumberInterface multiplier);
|
|
|
|
|
|
|
|
public final NumberInterface multiply(NumberInterface multiplier){
|
|
|
|
checkInterrupted();
|
|
|
|
return multiplyInternal(multiplier);
|
|
|
|
}
|
2017-07-30 21:11:32 -07:00
|
|
|
|
2017-07-25 22:47:48 -07:00
|
|
|
/**
|
|
|
|
* Divides this number by another, returning
|
|
|
|
* a new number instance.
|
2017-07-30 21:11:32 -07:00
|
|
|
*
|
2017-07-25 22:47:48 -07:00
|
|
|
* @param divisor the divisor
|
|
|
|
* @return the result of the division.
|
|
|
|
*/
|
2017-08-05 13:54:06 -07:00
|
|
|
protected abstract NumberInterface divideInternal(NumberInterface divisor);
|
|
|
|
|
|
|
|
public final NumberInterface divide(NumberInterface divisor){
|
|
|
|
checkInterrupted();
|
|
|
|
return divideInternal(divisor);
|
|
|
|
}
|
2017-07-30 21:11:32 -07:00
|
|
|
|
2017-07-25 22:47:48 -07:00
|
|
|
/**
|
|
|
|
* Adds this number to another, returning
|
|
|
|
* a new number instance.
|
2017-07-30 21:11:32 -07:00
|
|
|
*
|
2017-07-25 22:47:48 -07:00
|
|
|
* @param summand the summand
|
|
|
|
* @return the result of the summation.
|
|
|
|
*/
|
2017-08-05 13:54:06 -07:00
|
|
|
protected abstract NumberInterface addInternal(NumberInterface summand);
|
|
|
|
|
|
|
|
public final NumberInterface add(NumberInterface summand){
|
|
|
|
checkInterrupted();
|
|
|
|
return addInternal(summand);
|
|
|
|
}
|
2017-07-30 21:11:32 -07:00
|
|
|
|
2017-07-25 22:47:48 -07:00
|
|
|
/**
|
|
|
|
* Subtracts another number from this number,
|
|
|
|
* a new number instance.
|
2017-07-30 21:11:32 -07:00
|
|
|
*
|
2017-07-25 22:47:48 -07:00
|
|
|
* @param subtrahend the subtrahend.
|
|
|
|
* @return the result of the subtraction.
|
|
|
|
*/
|
2017-08-05 13:54:06 -07:00
|
|
|
protected abstract NumberInterface subtractInternal(NumberInterface subtrahend);
|
|
|
|
|
|
|
|
public final NumberInterface subtract(NumberInterface subtrahend){
|
|
|
|
checkInterrupted();
|
|
|
|
return subtractInternal(subtrahend);
|
|
|
|
}
|
2017-07-25 22:47:48 -07:00
|
|
|
|
|
|
|
/**
|
|
|
|
* Returns a new instance of this number with
|
|
|
|
* the sign flipped.
|
2017-07-30 21:11:32 -07:00
|
|
|
*
|
2017-07-25 22:47:48 -07:00
|
|
|
* @return the new instance.
|
|
|
|
*/
|
2017-08-05 13:54:06 -07:00
|
|
|
protected abstract NumberInterface negateInternal();
|
|
|
|
|
|
|
|
public final NumberInterface negate(){
|
|
|
|
checkInterrupted();
|
|
|
|
return negateInternal();
|
|
|
|
}
|
2017-07-25 22:47:48 -07:00
|
|
|
|
|
|
|
/**
|
|
|
|
* Raises this number to an integer power.
|
2017-07-30 21:11:32 -07:00
|
|
|
*
|
2017-07-26 19:28:57 -07:00
|
|
|
* @param exponent the exponent to which to take the number.
|
|
|
|
* @return the resulting value.
|
2017-07-25 22:47:48 -07:00
|
|
|
*/
|
2017-08-05 13:54:06 -07:00
|
|
|
protected abstract NumberInterface intPowInternal(int exponent);
|
|
|
|
|
|
|
|
public final NumberInterface intPow(int exponent){
|
|
|
|
checkInterrupted();
|
|
|
|
return intPowInternal(exponent);
|
|
|
|
}
|
2017-07-25 22:47:48 -07:00
|
|
|
|
|
|
|
/**
|
|
|
|
* Compares this number to another.
|
2017-07-30 21:11:32 -07:00
|
|
|
*
|
2017-07-25 22:47:48 -07:00
|
|
|
* @param number the number to compare to.
|
|
|
|
* @return same as Integer.compare();
|
|
|
|
*/
|
2017-08-05 13:54:06 -07:00
|
|
|
public abstract int compareTo(NumberInterface number);
|
2017-07-25 22:47:48 -07:00
|
|
|
|
|
|
|
/**
|
|
|
|
* Same as Math.signum().
|
2017-07-30 21:11:32 -07:00
|
|
|
*
|
2017-07-25 22:47:48 -07:00
|
|
|
* @return 1 if this number is positive, -1 if this number is negative, 0 if this number is 0.
|
|
|
|
*/
|
2017-08-05 13:54:06 -07:00
|
|
|
public abstract int signum();
|
2017-07-25 13:58:09 -07:00
|
|
|
|
2017-07-31 13:25:23 -07:00
|
|
|
/**
|
|
|
|
* Returns the least integer greater than or equal to the number.
|
2017-08-04 13:20:57 -07:00
|
|
|
*
|
2017-07-31 13:25:23 -07:00
|
|
|
* @return the least integer >= the number, if int can hold the value.
|
|
|
|
*/
|
2017-08-05 13:54:06 -07:00
|
|
|
protected abstract NumberInterface ceilingInternal();
|
|
|
|
|
|
|
|
public final NumberInterface ceiling(){
|
|
|
|
checkInterrupted();
|
|
|
|
return ceilingInternal();
|
|
|
|
}
|
2017-07-31 13:25:23 -07:00
|
|
|
|
2017-08-01 15:36:54 -07:00
|
|
|
/**
|
|
|
|
* Return the greatest integer less than or equal to the number.
|
2017-08-04 13:20:57 -07:00
|
|
|
*
|
2017-08-01 15:36:54 -07:00
|
|
|
* @return the greatest int >= the number, if int can hold the value.
|
|
|
|
*/
|
2017-08-05 13:54:06 -07:00
|
|
|
protected abstract NumberInterface floorInternal();
|
|
|
|
|
|
|
|
public final NumberInterface floor(){
|
|
|
|
checkInterrupted();
|
|
|
|
return floorInternal();
|
|
|
|
}
|
2017-08-02 12:00:56 -07:00
|
|
|
|
|
|
|
/**
|
|
|
|
* Returns the fractional part of the number.
|
2017-08-04 13:20:57 -07:00
|
|
|
*
|
2017-08-02 12:00:56 -07:00
|
|
|
* @return the fractional part of the number.
|
|
|
|
*/
|
2017-08-05 13:54:06 -07:00
|
|
|
protected abstract NumberInterface fractionalPartInternal();
|
|
|
|
|
|
|
|
public final NumberInterface fractionalPart(){
|
|
|
|
checkInterrupted();
|
|
|
|
return fractionalPartInternal();
|
|
|
|
}
|
2017-08-02 12:00:56 -07:00
|
|
|
|
|
|
|
/**
|
|
|
|
* Returns the integer representation of this number, discarding any fractional part,
|
|
|
|
* if int can hold the value.
|
2017-08-04 13:20:57 -07:00
|
|
|
*
|
2017-08-02 12:00:56 -07:00
|
|
|
* @return
|
|
|
|
*/
|
2017-08-05 13:54:06 -07:00
|
|
|
public abstract int intValue();
|
2017-08-01 15:36:54 -07:00
|
|
|
|
2017-07-25 22:47:48 -07:00
|
|
|
/**
|
|
|
|
* Promotes this class to another number class.
|
2017-07-30 21:11:32 -07:00
|
|
|
*
|
2017-07-25 22:47:48 -07:00
|
|
|
* @param toClass the class to promote to.
|
|
|
|
* @return the resulting new instance.
|
|
|
|
*/
|
2017-08-05 13:54:06 -07:00
|
|
|
protected abstract NumberInterface promoteToInternal(Class<? extends NumberInterface> toClass);
|
|
|
|
|
|
|
|
public final NumberInterface promoteTo(Class<? extends NumberInterface> toClass) {
|
|
|
|
checkInterrupted();
|
|
|
|
return promoteToInternal(toClass);
|
|
|
|
}
|
2017-07-25 13:58:09 -07:00
|
|
|
|
|
|
|
}
|