Skip to content

Commit 7bcfe18

Browse files
committed
[NUMBERS-152] add a private constructor for already known reduced num and den, to avoid unneeded gcd.
1 parent c3d173a commit 7bcfe18

1 file changed

Lines changed: 33 additions & 9 deletions

File tree

  • commons-numbers-fraction/src/main/java/org/apache/commons/numbers/fraction

commons-numbers-fraction/src/main/java/org/apache/commons/numbers/fraction/Fraction.java

Lines changed: 33 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -105,6 +105,30 @@ private Fraction(int num, int den) {
105105
}
106106
}
107107

108+
/**
109+
* Private constructor: Instances are created using factory methods.
110+
*
111+
* <p>This constructor should only be invoked when the fraction is known
112+
* to be already reduced, and non-ZERO;
113+
* otherwise use {@link #Fraction(int, int)}, or {@link #ZERO}.
114+
*
115+
* @param num Numerator.
116+
* @param den Denominator.
117+
* @param ignore Ignored, do not really use this, just to make it can overload.
118+
*/
119+
private Fraction(int num, int den, boolean ignore) {
120+
if (den == 0) {
121+
throw new FractionException(FractionException.ERROR_ZERO_DENOMINATOR);
122+
}
123+
if (num == den) {
124+
numerator = 1;
125+
denominator = 1;
126+
} else {
127+
numerator = num;
128+
denominator = den;
129+
}
130+
}
131+
108132
/**
109133
* Private constructor: Instances are created using factory methods.
110134
*
@@ -470,8 +494,8 @@ public Fraction abs() {
470494
@Override
471495
public Fraction negate() {
472496
return numerator == Integer.MIN_VALUE ?
473-
new Fraction(numerator, -denominator) :
474-
new Fraction(-numerator, denominator);
497+
new Fraction(numerator, -denominator, false) :
498+
new Fraction(-numerator, denominator, false);
475499
}
476500

477501
/**
@@ -483,7 +507,7 @@ public Fraction negate() {
483507
*/
484508
@Override
485509
public Fraction reciprocal() {
486-
return new Fraction(denominator, numerator);
510+
return new Fraction(denominator, numerator, false);
487511
}
488512

489513
/**
@@ -581,7 +605,7 @@ public Fraction subtract(final int value) {
581605
if (isZero()) {
582606
// Special case for min value
583607
return value == Integer.MIN_VALUE ?
584-
new Fraction(Integer.MIN_VALUE, -1) :
608+
new Fraction(Integer.MIN_VALUE, -1, false) :
585609
new Fraction(-value);
586610
}
587611
// Convert to numerator with same effective denominator
@@ -674,7 +698,7 @@ public Fraction multiply(final int value) {
674698
// (see multiply(Fraction) using value / 1 as the argument).
675699
final int d2 = ArithmeticUtils.gcd(value, denominator);
676700
return new Fraction(Math.multiplyExact(numerator, value / d2),
677-
denominator / d2);
701+
denominator / d2, false);
678702
}
679703

680704
/**
@@ -740,7 +764,7 @@ public Fraction divide(final int value) {
740764
// (see multiply(Fraction) using 1 / value as the argument).
741765
final int d1 = ArithmeticUtils.gcd(numerator, value);
742766
return new Fraction(numerator / d1,
743-
Math.multiplyExact(denominator, value / d1));
767+
Math.multiplyExact(denominator, value / d1), false);
744768
}
745769

746770
/**
@@ -789,18 +813,18 @@ public Fraction pow(final int exponent) {
789813
}
790814
if (exponent > 0) {
791815
return new Fraction(ArithmeticUtils.pow(numerator, exponent),
792-
ArithmeticUtils.pow(denominator, exponent));
816+
ArithmeticUtils.pow(denominator, exponent), false);
793817
}
794818
if (exponent == -1) {
795819
return this.reciprocal();
796820
}
797821
if (exponent == Integer.MIN_VALUE) {
798822
// MIN_VALUE can't be negated
799823
return new Fraction(ArithmeticUtils.pow(denominator, Integer.MAX_VALUE) * denominator,
800-
ArithmeticUtils.pow(numerator, Integer.MAX_VALUE) * numerator);
824+
ArithmeticUtils.pow(numerator, Integer.MAX_VALUE) * numerator, false);
801825
}
802826
return new Fraction(ArithmeticUtils.pow(denominator, -exponent),
803-
ArithmeticUtils.pow(numerator, -exponent));
827+
ArithmeticUtils.pow(numerator, -exponent), false);
804828
}
805829

806830
/**

0 commit comments

Comments
 (0)