//  Rational.java: Represent rational number with numerator and denominator.
public class Rational implements Comparable {
   private int numerator;
   private int denominator;

   // Rational: ensuring a nonzero denominator, make only numerator signed.
   public Rational(int numer, int denom) {
      if (denom == 0)
         denom = 1;
      // Make the numerator "store" the sign
      if (denom < 0) {
         numer = numer * -1;
         denom = denom * -1;
      }
      numerator = numer;
      denominator = denom;
      reduce();
   }

   //  add: add two rational numbers
   public Rational add(Rational op2) {
      int commonDenominator = denominator * op2.getDenominator();
      int numerator1 = numerator * op2.getDenominator();
      int numerator2 = op2.getNumerator() * denominator;
      int sum = numerator1 + numerator2;

      return new Rational (sum, commonDenominator);
   }

   //  subtract: subtract two rational numbers
   public Rational subtract(Rational op2) {
      int commonDenominator = denominator * op2.getDenominator();
      int numerator1 = numerator * op2.getDenominator();
      int numerator2 = op2.getNumerator() * denominator;
      int difference = numerator1 - numerator2;
      return new Rational(difference, commonDenominator);
   }

   //  multiply: multiply two rational numbers
   public Rational multiply(Rational op2) {
      int numer = numerator * op2.getNumerator();
      int denom = denominator * op2.getDenominator();
      return new Rational(numer, denom);
   }

   //  divide: divide two rational numbers
   public Rational divide(Rational op2) {
      return multiply(op2.reciprocal());
   }

   // reciprocal: take reciprocal
   public Rational reciprocal () {
      return new Rational(denominator, numerator);
   }

   // getNumerator: return the numerator
   public int getNumerator() {
      return numerator;
   }

   // getDenominator: return the denominator
   public int getDenominator() {
      return denominator;
   }

   // equals: check for equality
   public boolean equals(Rational op2) {
      return ( numerator == op2.getNumerator() &&
               denominator == op2.getDenominator() );
   }

   // toString: convert to String
   public String toString() {
      String result;
      if (numerator == 0)
         result = "0";
      else
         if (denominator == 1)
            result = numerator + "";
         else
            result = numerator + "/" + denominator;
          return result;
   }

   // reduce: reduce to lowest terms
   private void reduce() {
      if (numerator != 0) {
         int common = gcd (Math.abs(numerator), denominator);

         numerator = numerator / common;
         denominator = denominator / common;
      }
   }

   // gcd: greatest commmon divisor
   private int gcd(int num1, int num2) {
      while (num1 != num2)
         if (num1 > num2)
            num1 = num1 - num2;
         else
            num2 = num2 - num1;
      return num1;
   }

   // compareTo: the method in Comparable interface
   public int compareTo(Object obj) {
      Rational diff = this.subtract((Rational)obj);
      if (diff.numerator == 0) return 0;
      else if (diff.numerator < 0) return -1;
      else return 1;
   }
}
