BigRational.parseDecimal constructor

BigRational.parseDecimal(
  1. String decimal
)

Parses a decimal string and constructs a BigRational instance from it.

This method parses the given decimal string and constructs a BigRational representing the decimal value it contains. It supports parsing decimal strings in scientific, floating point, and integer notation.

decimal The decimal string to be parsed. returns A BigRational instance representing the parsed decimal value.

Implementation

factory BigRational.parseDecimal(String decimal) {
  List<String> parts = decimal.split(RegExp(r'e', caseSensitive: false));
  if (parts.length > 2) {
    throw const ArgumentException("Invalid input: too many 'e' tokens");
  }

  if (parts.length > 1) {
    bool isPositive = true;
    if (parts[1][0] == "-") {
      parts[1] = parts[1].substring(1);
      isPositive = false;
    }
    if (parts[1][0] == "+") {
      parts[1] = parts[1].substring(1);
    }
    final BigRational significand = BigRational.parseDecimal(parts[0]);
    final BigRational exponent =
        BigRational._(_ten.pow(int.parse(parts[1])), _one);
    if (isPositive) {
      return significand * exponent;
    } else {
      return significand / exponent;
    }
  }

  parts = decimal.trim().split(".");
  if (parts.length > 2) {
    throw const ArgumentException("Invalid input: too many '.' tokens");
  }
  if (parts.length > 1) {
    final bool isNegative = parts[0][0] == '-';
    if (isNegative) parts[0] = parts[0].substring(1);
    BigRational intPart = BigRational._(BigInt.parse(parts[0]), _one);
    final int length = parts[1].length;
    while (parts[1].isNotEmpty && parts[1][0] == "0") {
      parts[1] = parts[1].substring(1);
    }

    final String exp = "1${"0" * length}";
    final BigRational decPart = _reduce(
        parts[1].isEmpty ? _zero : BigInt.parse(parts[1]), BigInt.parse(exp));
    intPart = intPart + decPart;
    if (isNegative) intPart = ~intPart;
    return intPart;
  }

  return BigRational._(BigInt.parse(decimal), _one);
}