static string InternalToString(BigRational r, int precision) { var fraction = r.GetFractionPart(); // Case where the rational number is a whole number // Niko: Incorrect check? F**k it... This works... if (fraction.Numerator == 0 && fraction.Denominator == 1) { return(r.GetWholePart().ToString()); } BigInteger adjustedNumerator = fraction.Numerator * BigInteger.Pow(10, precision); // Abs fixes decimals having minuses in front of them BigInteger decimalPlaces = BigInteger.Abs(adjustedNumerator / fraction.Denominator); // Case where precision wasn't large enough. if (decimalPlaces == 0) { return(null); } // Give it the capacity for around what we should need for // the whole part and total precision // (this is kinda sloppy, but does the trick) var sb = new StringBuilder(precision + r.ToString().Length); bool noMoreTrailingZeros = false; for (int i = precision; i > 0; i--) { if (!noMoreTrailingZeros) { if ((decimalPlaces % 10) == 0) { decimalPlaces /= 10; continue; } noMoreTrailingZeros = true; } // Add the right most decimal to the string sb.Insert(0, decimalPlaces % 10); decimalPlaces /= 10; } // Insert the whole part and decimal sb.Insert(0, ","); sb.Insert(0, r.GetWholePart()); return(sb.ToString()); }
public static string ToDecimalString(this BigRational r, int precision) { var fraction = r.GetFractionPart(); // Case where the rational number is a whole number if (fraction.Numerator == 0 && fraction.Denominator == 1) { return(r.GetWholePart() + ".0"); } var adjustedNumerator = (fraction.Numerator * BigInteger.Pow(10, precision)); var decimalPlaces = adjustedNumerator / fraction.Denominator; // Case where precision wasn't large enough. if (decimalPlaces == 0) { return("0.0"); } // Give it the capacity for around what we should need for // the whole part and total precision // (this is kinda sloppy, but does the trick) var sb = new StringBuilder(precision + r.ToString().Length); bool noMoreTrailingZeros = false; for (int i = precision; i > 0; i--) { if (!noMoreTrailingZeros) { if ((decimalPlaces % 10) == 0) { decimalPlaces = decimalPlaces / 10; continue; } noMoreTrailingZeros = true; } // Add the right most decimal to the string sb.Insert(0, decimalPlaces % 10); decimalPlaces = decimalPlaces / 10; } // Insert the whole part and decimal sb.Insert(0, "."); sb.Insert(0, r.GetWholePart()); return(sb.ToString()); }
private static string GetMixedFormat(BigRational value, char separator) { StringBuilder sb = new(); BigInteger whole = value.GetWholePart(); BigRational fractionPart = value.GetFractionPart(); if (!whole.IsZero) { sb.Append(whole.ToString("R", CultureInfo.CurrentCulture)); if (separator != DisplaySeparator) { sb.Append(separator); } else { // When the DisplaySeparator is being used, // then the whole and fractional parts need // to be separated by whitespace. sb.Append(' '); } // If the rational number was negative, then the // whole part will have been rendered as a negative // number, so we need to ensure that the fractional // part doesn't render as a negative value too. fractionPart = BigRational.Abs(fractionPart); } AppendCommonFormat(sb, fractionPart, separator); return(sb.ToString()); }
public static string ToDecimalString(this BigRational r, int numDigits) { var fraction = r.GetFractionPart(); var adjustedNumerator = (fraction.Numerator * BigInteger.Pow(10, numDigits)); var decimalPlaces = adjustedNumerator / fraction.Denominator; return(r.GetWholePart() + "." + decimalPlaces); }
List <object> CalculateOperations(List <object> toCalculate, params Operation[] operations) { List <object> toC = new List <object>(toCalculate); for (int i = 0; i < toC.Count; i++) { object rawValue = toC[i]; if (rawValue is Operation value) { if (!operations.Contains(value)) { continue; } BigRational v1 = (BigRational)toC[i - 1]; BigRational v2 = (BigRational)toC[i + 1]; toC.RemoveAt(i + 1); // Before minus one so that the list isn't changed before removing this value. toC.RemoveAt(i - 1); i--; // To fix iteration switch (value) { case Operation.Multiply: toC[i] = v1 * v2; break; case Operation.Divide: toC[i] = v1 / v2; break; case Operation.Add: toC[i] = v1 + v2; break; case Operation.Substract: toC[i] = v1 - v2; break; case Operation.Exponent: if (v2.GetFractionPart() != BigRational.Zero) { throw new CalculationException("Decimal number exponents are not supported yet."); } toC[i] = BigRational.Pow(v1, v2.GetWholePart()); break; case Operation.Unspecified: throw new CalculationException("Unspecified operations should be replaced before calling CalculateOperations!"); default: throw new CalculationException("Invalid operation type!"); } } } return(toC); }
public void big_rational_methods() { BigRational big = new BigRational(3, 2); Assert.NotNull(big.ToString()); Assert.AreEqual(1, (double)big.GetWholePart()); Assert.AreEqual(0.5, (double)big.GetFractionPart()); Assert.AreEqual(new BigRational(3, 2).GetHashCode(), big.GetHashCode()); Assert.True(new BigRational(3, 2).Equals(big)); Assert.True(new BigRational(6, 4).Equals(big)); Assert.False(new BigRational(6, 4).Equals(new object())); Assert.False(new BigRational(6, 4).Equals(null)); Assert.AreEqual(1, new HashSet <BigRational> { big, new BigRational(3, 2) }.Count); Assert.AreEqual(0.25, (double)(new List <BigRational> { big, new BigRational(1, 4) }.OrderBy(r => r).First())); }
public static string ToDecimalString(this BigRational r, int numDigits) { var fraction = r.GetFractionPart(); var adjustedNumerator = (fraction.Numerator * BigInteger.Pow(10, numDigits)); var decimalPlaces = adjustedNumerator / fraction.Denominator; // Give it the capacity for around what we should need for // the whole part and total precision // (this is kinda sloppy, but does the trick) var sb = new StringBuilder(numDigits + r.ToString().Length); bool noMoreTrailingZeros = false; for (int i = numDigits; i > 0; i--) { if (!noMoreTrailingZeros) { if ((decimalPlaces % 10) == 0) { decimalPlaces = decimalPlaces / 10; continue; } noMoreTrailingZeros = true; } // Add the right most decimal to the string sb.Insert(0, decimalPlaces % 10); decimalPlaces = decimalPlaces / 10; } // If the precision wasn't high enough, sb will // have a length of 0. if (sb.Length == 0) { return("0.0"); } // Insert the whole part and decimal sb.Insert(0, "."); sb.Insert(0, r.GetWholePart()); return(sb.ToString()); }
public static BigRational Floor(this BigRational num) { return((num.Sign >= 0 || num.GetFractionPart() == BigRational.Zero) ? num.GetWholePart() : num.GetWholePart() - 1); }
private static string FormatBigRational(BigRational x, int digits) { // Let the magic begin: BigInteger shiftedBigInteger = x.Numerator * BigInteger.Pow(10, digits); string formatString = (shiftedBigInteger / x.Denominator).ToString(); var sb = new StringBuilder(digits); sb.Append(x.GetWholePart().ToString()); int wholePart = sb.Length; sb.Append('.'); sb.Append(formatString.Substring(1, formatString.Length - wholePart)); return sb.ToString(); }