程序小白,希望和大家多交流,共同学习
设计一个Rational类,用于表示和处理有理数。
因为有理数共享了很多整数和浮点数的通用特征,而且Number是数值包装类的根类,所以讲Rational类定义为Number类的子类,因为有理数是可以比较的,所以Rational类也应该能够实现Comparable接口。
使用BigInteger实现数据类型。
import java.math.BigInteger;
import java.math.BigDecimal;
public class Rational extends Number implements Comparable<Rational>
{
private BigInteger numerator = new BigInteger("0");
private BigInteger denominator = new BigInteger("1");
public Rational()
{
this(new BigInteger("0"), new BigInteger("1"));
}
public Rational (BigInteger numerator, BigInteger denominator)
{
//System.out.println(numerator.toString() + " " + denominator.toString());
BigInteger gcd = gcd(numerator, denominator);
if (denominator.compareTo(new BigInteger("0")) > 0)
{
this.numerator = numerator.divide(gcd);
}
else
numerator = numerator.multiply(new BigInteger("-1")).divide(gcd);
this.denominator = denominator.abs().divide(gcd);
//System.out.println(this.numerator.toString() + " " + this.denominator.toString());
}
private static BigInteger gcd (BigInteger n, BigInteger d)
{
BigInteger n1 = n.abs();
BigInteger n2 = d.abs();
BigInteger gcd = new BigInteger("1");
BigInteger k2 = new BigInteger("1");
for (int k = 1; k <= n1.intValue() && k <= n2.intValue(); k++)
{
if ((n1.remainder(k2).equals(new BigInteger("0"))) &&
(n2.remainder(k2).equals(new BigInteger("0"))))
{
gcd = k2;
}
k2 = k2.add(new BigInteger("1"));
//System.out.println(k2.toString() + " " + n1.toString() + " " + n2.toString());
}
return gcd;
}
public BigInteger getNumerator()
{
return numerator;
}
public BigInteger getDenominator()
{
return denominator;
}
public Rational add(Rational secondRational)
{
BigInteger n = numerator.multiply(secondRational.getDenominator()).add(denominator.multiply(secondRational.getNumerator()));
BigInteger d = denominator.multiply(secondRational.getDenominator());
return new Rational(n, d);
}
public Rational subtract(Rational secondRational)
{
BigInteger n = numerator.multiply(secondRational.getDenominator()).subtract(denominator.multiply(secondRational.getNumerator()));
BigInteger d = denominator.multiply(secondRational.getDenominator());
return new Rational(n, d);
}
public Rational multiply(Rational secondRational)
{
BigInteger n = numerator.multiply(secondRational.getNumerator());
BigInteger d = denominator.multiply(secondRational.getDenominator());
//System.out.println(numerator.toString() + " " + denominator.toString());
return new Rational(n, d);
}
public Rational divide(Rational secondRational)
{
BigInteger n = numerator.multiply(secondRational.getDenominator());
BigInteger d = denominator.multiply(secondRational.getNumerator());
return new Rational(n, d);
}
@Override
public String toString()
{
if (denominator.equals(new BigInteger("1")))
{
return numerator.toString();
}
else
return numerator.toString() + "/" + denominator.toString();
}
@Override
public boolean equals(Object other)
{
if (this.subtract((Rational)other).getNumerator().equals(new BigInteger("0")))
{
return true;
}
else
return false;
}
@Override
public int intValue()
{
return (int)doubleValue();
}
@Override
public float floatValue()
{
return (float)doubleValue();
}
@Override
public double doubleValue()
{
return numerator.divide(denominator).doubleValue();
}
@Override
public long longValue()
{
return (long)doubleValue();
}
@Override
public int compareTo(Rational o)
{
if (this.subtract(o).getNumerator().compareTo(new BigInteger("0")) > 0)
{
return 1;
}
else if (this.subtract(o).getNumerator().compareTo(new BigInteger("0")) < 0)
{
return -1;
}
else
return 0;
}
}
测试类
import java.math.BigInteger;
public class TestRational
{
public static void main(String [] args)
{
BigInteger numerator = new BigInteger("1");
BigInteger denominator = new BigInteger("123456789");
Rational r1 = new Rational(numerator, denominator);
Rational r2 = new Rational(numerator, denominator);
Rational r3 = new Rational(numerator, denominator);
System.out.println("r1 * r2 * r3 is " + r1.multiply(r2.multiply(r3)));
}
}