package st.gravel.support.jvm;
import java.math.BigInteger;
public class LargeIntegerExtensions {
public static class Factory extends IntegerExtensions.Factory {
}
public static double asDouble(BigInteger receiver) {
return receiver.doubleValue();
}
public static float asFloat(BigInteger receiver) {
return receiver.floatValue();
}
public static Number bitAndFromLargeInteger_(BigInteger receiver,
BigInteger operand) {
return IntegerExtensions.objectFromBigInteger(operand.and(receiver));
}
public static int bitAndFromPositiveSmallInteger_(BigInteger receiver,
int operand) {
return operand & receiver.intValue();
}
public static Number bitAndFromSmallInteger_(BigInteger receiver,
int operand) {
return bitAndFromLargeInteger_(receiver, BigInteger.valueOf(operand));
}
public static int bitAt_(BigInteger receiver, int operand) {
return (receiver.testBit(operand)) ? 1 : 0;
}
public static Number bitAt_put_(BigInteger receiver, int bitIndex,
int bitValue) {
if (bitValue == 1) {
return IntegerExtensions.objectFromBigInteger(receiver
.setBit(bitIndex));
} else if (bitValue == 0) {
return IntegerExtensions.objectFromBigInteger(receiver
.clearBit(bitIndex));
} else {
throw new RuntimeException();
}
}
public static BigInteger bitInvert(BigInteger receiver) {
return receiver.not();
}
public static BigInteger bitOrFromLargeInteger_(BigInteger receiver,
BigInteger operand) {
return operand.or(receiver);
}
public static Number bitOrFromSmallInteger_(BigInteger receiver, int operand) {
return IntegerExtensions.objectFromBigInteger(((BigInteger
.valueOf(operand)).or(receiver)));
}
public static Number bitShift_(BigInteger receiver, int operand) {
return IntegerExtensions.objectFromBigInteger(receiver
.shiftLeft(operand));
}
public static Number bitXorFromLargeInteger_(BigInteger receiver,
BigInteger operand) {
return IntegerExtensions.objectFromBigInteger(operand.xor(receiver));
}
public static Number bitXorFromSmallInteger_(BigInteger receiver,
int operand) {
return bitXorFromLargeInteger_(receiver, BigInteger.valueOf(operand));
}
public static Object compressed(BigInteger integer) {
return Factory.fromValue(integer);
}
public static Number differenceFromLargeInteger_(BigInteger receiver,
BigInteger argument) {
return IntegerExtensions.objectFromBigInteger(argument
.subtract(receiver));
}
public static Number differenceFromSmallInteger_(BigInteger receiver,
int argument) {
return IntegerExtensions.objectFromBigInteger(BigInteger.valueOf(
argument).subtract(receiver));
}
public static double doubleDivFromLargeInteger_(BigInteger receiver,
BigInteger argument) {
return (argument.doubleValue() / receiver.doubleValue());
}
public static double doubleDivFromSmallInteger_(BigInteger receiver,
int argument) {
return (double) argument / receiver.doubleValue();
}
public static boolean equals_(BigInteger receiver, BigInteger other) {
return (receiver == null && other == null)
|| (receiver != null && other != null && receiver.equals(other));
}
public static float floatDivFromLargeInteger_(BigInteger receiver,
BigInteger argument) {
return (float) (argument.doubleValue() / receiver.doubleValue());
}
public static float floatDivFromSmallInteger_(BigInteger receiver,
int argument) {
return (float) ((double) argument / receiver.doubleValue());
}
public static Number gcdFromLargeInteger_(BigInteger receiver,
BigInteger argument) {
return IntegerExtensions.objectFromBigInteger(argument.gcd(receiver));
}
public static Number gcdFromSmallInteger_(BigInteger receiver, int argument) {
return gcdFromLargeInteger_(receiver, BigInteger.valueOf(argument));
}
public static int highBit(BigInteger receiver) {
if (receiver.signum() == -1)
throw new RuntimeException("should be positive");
return receiver.bitLength();
}
public static Number integerQuotientFromLargeInteger_(BigInteger y,
BigInteger x) {
return IntegerExtensions.objectFromBigInteger(divRoundToNegInfinity(x, y));
}
private static BigInteger divRoundToNegInfinity(BigInteger x, BigInteger y) {
// http://www.microhowto.info/howto/round_towards_minus_infinity_when_dividing_integers_in_java.html
if (y.signum() >= 0) {
if (x.signum() >= 0) {
return x.divide(y);
} else {
return ((x.add(BigInteger.ONE)).divide(y)).subtract(BigInteger.ONE);
}
} else {
if (x.signum() == 1) {
//return -1-((1-x)/y);
return BigInteger.ONE.negate().subtract(((BigInteger.ONE.subtract(x)).divide(y)));
} else {
return x.divide(y);
}
}
}
public static Number integerQuotientFromSmallInteger_(BigInteger receiver,
int argument) {
if (argument == 0)
return 0;
return integerQuotientFromLargeInteger_(receiver,
BigInteger.valueOf(argument));
}
public static boolean isSmallerThan_(BigInteger receiver, Object other) {
if (other instanceof BigInteger)
return receiver.compareTo((BigInteger) other) < 0;
return receiver.compareTo(BigInteger.valueOf((Integer) other)) < 0;
}
public static boolean lessFromLargeInteger_(BigInteger receiver,
BigInteger argument) {
return argument.compareTo(receiver) == -1;
}
public static boolean lessFromSmallInteger_(BigInteger receiver,
Integer argument) {
return BigInteger.valueOf((int) argument).compareTo(receiver) == -1;
}
public static Number moduloQuotientFromLargeInteger_(BigInteger n,
BigInteger x) {
BigInteger r = x.remainder(n);
if (x.signum() != n.signum())
return IntegerExtensions.objectFromBigInteger(r.add(n));
return IntegerExtensions.objectFromBigInteger(r);
}
public static Number moduloQuotientFromSmallInteger_(BigInteger receiver,
int argument) {
if (argument == 0)
return 0;
return moduloQuotientFromLargeInteger_(receiver,
BigInteger.valueOf(argument));
}
public static BigInteger multiply_(BigInteger receiver, BigInteger argument) {
// only used by parser
return argument.multiply(receiver);
}
public static BigInteger multiply_(BigInteger receiver, int argument) {
// only used by parser
return BigInteger.valueOf(argument).multiply(receiver);
}
public static BigInteger plus_(BigInteger receiver, BigInteger argument) {
// only used by parser (so no compression needed)
return argument.add(receiver);
}
public static BigInteger plus_(BigInteger receiver, int argument) {
// only used by parser (so no compression needed)
return BigInteger.valueOf(argument).add(receiver);
}
public static String printBase_(BigInteger receiver, int radix) {
return receiver.toString(radix);
}
public static BigInteger productFromLargeInteger_(BigInteger receiver,
BigInteger argument) {
return argument.multiply(receiver);
}
public static Number productFromSmallInteger_(BigInteger receiver,
int argument) {
if (argument == 0)
return 0;
return BigInteger.valueOf(argument).multiply(receiver);
}
public static Number quoFromLargeInteger_(BigInteger receiver,
BigInteger argument) {
return IntegerExtensions
.objectFromBigInteger(argument.divide(receiver));
}
public static Number quoFromSmallInteger_(BigInteger receiver, int argument) {
return IntegerExtensions.objectFromBigInteger(BigInteger.valueOf(
argument).divide(receiver));
}
public static Number remFromLargeInteger_(BigInteger receiver,
BigInteger argument) {
return IntegerExtensions.objectFromBigInteger(argument
.remainder(receiver));
}
public static Number remFromSmallInteger_(BigInteger receiver, int argument) {
return IntegerExtensions.objectFromBigInteger(BigInteger.valueOf(
argument).remainder(receiver));
}
public static BigInteger sumFromLargeInteger_(BigInteger receiver,
BigInteger argument) {
return argument.add(receiver);
}
public static Number sumFromSmallInteger_(BigInteger receiver, int argument) {
return IntegerExtensions.objectFromBigInteger(BigInteger.valueOf(
argument).add(receiver));
}
public static boolean isZero(BigInteger receiver) {
return receiver.equals(BigInteger.ZERO);
}
}