package org.jcodec.common.model;
import static org.jcodec.common.StringUtils.splitS;
import org.jcodec.common.tools.MathUtil;
/**
* This class is part of JCodec ( www.jcodec.org ) This software is distributed
* under FreeBSD License
*
* @author The JCodec project
*
*/
public class RationalLarge {
public static final RationalLarge ONE = new RationalLarge(1, 1);
public static final RationalLarge HALF = new RationalLarge(1, 2);
public static final RationalLarge ZERO = new RationalLarge(0, 1);
final long num;
final long den;
public RationalLarge(long num, long den) {
this.num = num;
this.den = den;
}
public long getNum() {
return num;
}
public long getDen() {
return den;
}
public static RationalLarge parse(String string) {
String[] split = splitS(string, ":");
return split.length > 1 ? RationalLarge.R(Long.parseLong(split[0]), Long.parseLong(split[1])) : RationalLarge
.R(Long.parseLong(string), 1);
}
@Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + (int) (den ^ (den >>> 32));
result = prime * result + (int) (num ^ (num >>> 32));
return result;
}
@Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
RationalLarge other = (RationalLarge) obj;
if (den != other.den)
return false;
if (num != other.num)
return false;
return true;
}
public long multiplyS(long scalar) {
return (num * scalar) / den;
}
public long divideS(long scalar) {
return (den * scalar) / num;
}
public long divideByS(long scalar) {
return num / (den * scalar);
}
public RationalLarge flip() {
return new RationalLarge(den, num);
}
public static RationalLarge R(long num, long den) {
return new RationalLarge(num, den);
}
public static RationalLarge R1(long num) {
return R(num, 1);
}
public boolean lessThen(RationalLarge sec) {
return num * sec.den < sec.num * den;
}
public boolean greaterThen(RationalLarge sec) {
return num * sec.den > sec.num * den;
}
public boolean smallerOrEqualTo(RationalLarge sec) {
return num * sec.den <= sec.num * den;
}
public boolean greaterOrEqualTo(RationalLarge sec) {
return num * sec.den >= sec.num * den;
}
public boolean equalsLarge(RationalLarge other) {
return num * other.den == other.num * den;
}
public RationalLarge plus(RationalLarge other) {
return reduceLong(num * other.den + other.num * den, den * other.den);
}
public RationalLarge plusR(Rational other) {
return reduceLong(num * other.den + other.num * den, den * other.den);
}
public RationalLarge minus(RationalLarge other) {
return reduceLong(num * other.den - other.num * den, den * other.den);
}
public RationalLarge minusR(Rational other) {
return reduceLong(num * other.den - other.num * den, den * other.den);
}
public RationalLarge plusLong(long scalar) {
return new RationalLarge(num + scalar * den, den);
}
public RationalLarge minusLong(long scalar) {
return new RationalLarge(num - scalar * den, den);
}
public RationalLarge multiplyLong(long scalar) {
return new RationalLarge(num * scalar, den);
}
public RationalLarge divideLong(long scalar) {
return new RationalLarge(den * scalar, num);
}
public RationalLarge divideByLong(long scalar) {
return new RationalLarge(num, den * scalar);
}
public RationalLarge multiply(RationalLarge other) {
return reduceLong(num * other.num, den * other.den);
}
public RationalLarge multiplyR(Rational other) {
return reduceLong(num * other.num, den * other.den);
}
public RationalLarge divideRL(RationalLarge other) {
return reduceLong(other.num * den, other.den * num);
}
public RationalLarge divideR(Rational other) {
return reduceLong(other.num * den, other.den * num);
}
public RationalLarge divideBy(RationalLarge other) {
return reduceLong(num * other.den, den * other.num);
}
public RationalLarge divideByR(Rational other) {
return reduceLong(num * other.den, den * other.num);
}
public double scalar() {
return ((double) num) / den;
}
public long scalarClip() {
return num / den;
}
@Override
public String toString() {
return num + ":" + den;
}
public static RationalLarge reduceLong(long num, long den) {
long gcd = MathUtil.gcdLong(num, den);
return new RationalLarge(num / gcd, den / gcd);
}
}