1 9 package javax.measure.converters; 10 11 21 public final class RationalConverter extends UnitConverter { 22 23 26 private final long _dividend; 27 28 31 private final long _divisor; 32 33 42 public RationalConverter(long dividend, long divisor) { 43 if (divisor < 0) 44 throw new IllegalArgumentException ("Negative divisor"); 45 if (dividend == divisor) 46 throw new IllegalArgumentException ("Identity converter not allowed"); 47 _dividend = dividend; 48 _divisor = divisor; 49 } 50 51 56 public long getDividend() { 57 return _dividend; 58 } 59 60 65 public long getDivisor() { 66 return _divisor; 67 } 68 69 @Override 70 public UnitConverter inverse() { 71 return _dividend < 0 ? new RationalConverter(-_divisor, -_dividend) 72 : new RationalConverter(_divisor, _dividend); 73 } 74 75 @Override 76 public double convert(double amount) { 77 return amount * _dividend / _divisor; 78 } 79 80 @Override 81 public boolean isLinear() { 82 return true; 83 } 84 85 @Override 86 public boolean equals(Object cvtr) { 87 if (!(cvtr instanceof RationalConverter)) 88 return false; 89 RationalConverter rc = (RationalConverter) cvtr; 90 return (_dividend == rc._dividend) && (_divisor == rc._divisor); 91 } 92 93 @Override 94 public int hashCode() { 95 long value = _dividend - _divisor; 96 int h = (int) (value ^ (value >>> 32)); 97 h += ~(h << 9); 98 h ^= (h >>> 14); 99 h += (h << 4); 100 return h ^ (h >>> 10); 101 } 102 103 @Override 104 public UnitConverter concatenate(UnitConverter converter) { 105 if (converter instanceof RationalConverter) { 106 RationalConverter that = (RationalConverter) converter; 107 long dividendLong = this._dividend * that._dividend; 108 long divisorLong = this._divisor * that._divisor; 109 double dividendDouble = ((double)this._dividend) * that._dividend; 110 double divisorDouble = ((double)this._divisor) * that._divisor; 111 if ((dividendLong != dividendDouble) || 112 (divisorLong != divisorDouble)) { return new MultiplyConverter(dividendDouble / divisorDouble); 114 } 115 long gcd = gcd(dividendLong, divisorLong); 116 return RationalConverter.valueOf(dividendLong / gcd, divisorLong / gcd); 117 } else if (converter instanceof MultiplyConverter) { 118 return converter.concatenate(this); 119 } else { 120 return super.concatenate(converter); 121 } 122 } 123 124 private static UnitConverter valueOf(long dividend, long divisor) { 125 return (dividend == 1L) && (divisor == 1L) ? UnitConverter.IDENTITY 126 : new RationalConverter(dividend, divisor); 127 } 128 129 136 private static long gcd(long m, long n) { 137 if (n == 0L) { 138 return m; 139 } else { 140 return gcd(n, m % n); 141 } 142 } 143 144 private static final long serialVersionUID = 1L; 145 } | Popular Tags |