// Copyright (c) 2012, the Dart project authors.  Please see the AUTHORS file
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.

part of dart.core;

/// An integer or floating-point number.
///
/// It is a compile-time error for any type other than [int] or [double]
/// to attempt to extend or implement `num`.
///
/// **See also:**
/// * [int]: An integer number.
/// * [double]: A double-precision floating point number.
/// * [Numbers](https://dart.dev/guides/language/numbers) in
/// [A tour of the Dart language](https://dart.dev/guides/language/language-tour).

abstract class num implements Comparable<num> {
  /// Test whether this value is numerically equal to `other`.
  ///
  /// If both operands are [double]s, they are equal if they have the same
  /// representation, except that:
  ///
  ///   * zero and minus zero (0.0 and -0.0) are considered equal. They
  ///     both have the numerical value zero.
  ///   * NaN is not equal to anything, including NaN. If either operand is
  ///     NaN, the result is always false.
  ///
  /// If one operand is a [double] and the other is an [int], they are equal if
  /// the double has an integer value (finite with no fractional part) and
  /// the numbers have the same numerical value.
  ///
  /// If both operands are integers, they are equal if they have the same value.
  ///
  /// Returns false if [other] is not a [num].
  ///
  /// Notice that the behavior for NaN is non-reflexive. This means that
  /// equality of double values is not a proper equality relation, as is
  /// otherwise required of `operator==`. Using NaN in, e.g., a [HashSet]
  /// will fail to work. The behavior is the standard IEEE-754 equality of
  /// doubles.
  ///
  /// If you can avoid NaN values, the remaining doubles do have a proper
  /// equality relation, and can be used safely.
  ///
  /// Use [compareTo] for a comparison that distinguishes zero and minus zero,
  /// and that considers NaN values as equal.
  bool operator ==(Object other);

  /// Returns a hash code for a numerical value.
  ///
  /// The hash code is compatible with equality. It returns the same value
  /// for an [int] and a [double] with the same numerical value, and therefore
  /// the same value for the doubles zero and minus zero.
  ///
  /// No guarantees are made about the hash code of NaN values.
  int get hashCode;

  /// Compares this to `other`.
  ///
  /// Returns a negative number if `this` is less than `other`, zero if they are
  /// equal, and a positive number if `this` is greater than `other`.
  ///
  /// The ordering represented by this method is a total ordering of [num]
  /// values. All distinct doubles are non-equal, as are all distinct integers,
  /// but integers are equal to doubles if they have the same numerical
  /// value.
  ///
  /// For doubles, the `compareTo` operation is different from the partial
  /// ordering given by [operator==], [operator<] and [operator>]. For example,
  /// IEEE doubles impose that `0.0 == -0.0` and all comparison operations on
  /// NaN return false.
  ///
  /// This function imposes a complete ordering for doubles. When using
  /// `compareTo`, the following properties hold:
  ///
  /// - All NaN values are considered equal, and greater than any numeric value.
  /// - -0.0 is less than 0.0 (and the integer 0), but greater than any non-zero
  ///    negative value.
  /// - Negative infinity is less than all other values and positive infinity is
  ///   greater than all non-NaN values.
  /// - All other values are compared using their numeric value.
  ///
  /// Examples:
  /// ```dart
  /// print(1.compareTo(2)); // => -1
  /// print(2.compareTo(1)); // => 1
  /// print(1.compareTo(1)); // => 0
  ///
  /// // The following comparisons yield different results than the
  /// // corresponding comparison operators.
  /// print((-0.0).compareTo(0.0));  // => -1
  /// print(double.nan.compareTo(double.nan));  // => 0
  /// print(double.infinity.compareTo(double.nan)); // => -1
  ///
  /// // -0.0, and NaN comparison operators have rules imposed by the IEEE
  /// // standard.
  /// print(-0.0 == 0.0); // => true
  /// print(double.nan == double.nan);  // => false
  /// print(double.infinity < double.nan);  // => false
  /// print(double.nan < double.infinity);  // => false
  /// print(double.nan == double.infinity);  // => false
  /// ```
  int compareTo(num other);

  /// Adds [other] to this number.
  ///
  /// The result is an [int], as described by [int.+],
  /// if both this number and [other] is an integer,
  /// otherwise the result is a [double].
  num operator +(num other);

  /// Subtracts [other] from this number.
  ///
  /// The result is an [int], as described by [int.-],
  /// if both this number and [other] is an integer,
  /// otherwise the result is a [double].
  num operator -(num other);

  /// Multiplies this number by [other].
  ///
  /// The result is an [int], as described by [int.*],
  /// if both this number and [other] are integers,
  /// otherwise the result is a [double].
  num operator *(num other);

  /// Euclidean modulo of this number by [other].
  ///
  /// Returns the remainder of the Euclidean division.
  /// The Euclidean division of two integers `a` and `b`
  /// yields two integers `q` and `r` such that
  /// `a == b * q + r` and `0 <= r < b.abs()`.
  ///
  /// The Euclidean division is only defined for integers, but can be easily
  /// extended to work with doubles. In that case, `q` is still an integer,
  /// but `r` may have a non-integer value that still satisfies `0 <= r < |b|`.
  ///
  /// The sign of the returned value `r` is always positive.
  ///
  /// See [remainder] for the remainder of the truncating division.
  ///
  /// The result is an [int], as described by [int.%],
  /// if both this number and [other] are integers,
  /// otherwise the result is a [double].
  ///
  /// Example:
  /// ```dart
  /// print(5 % 3); // 2
  /// print(-5 % 3); // 1
  /// print(5 % -3); // 2
  /// print(-5 % -3); // 1
  /// ```
 num operator %(num other);

  /// Divides this number by [other].
  double operator /(num other);

  /// Truncating division operator.
  ///
  /// Performs truncating division of this number by [other].
  /// Truncating division is division where a fractional result
  /// is converted to an integer by rounding towards zero.
  ///
  /// If both operands are [int]s, then [other] must not be zero.
  /// Then `a ~/ b` corresponds to `a.remainder(b)`
  /// such that `a == (a ~/ b) * b + a.remainder(b)`.
  ///
  /// If either operand is a [double], then the other operand is converted
  /// to a double before performing the division and truncation of the result.
  /// Then `a ~/ b` is equivalent to `(a / b).truncate()`.
  /// This means that the intermediate result of the double division
  /// must be a finite integer (not an infinity or [double.nan]).
  int operator ~/(num other);

  /// The negation of this value.
  ///
  /// The negation of a number is a number of the same kind
  /// (`int` or `double`) representing the negation of the
  /// numbers numerical value (the result of subtracting the
  /// number from zero), if that value *exists*.
  ///
  /// Negating a double gives a number with the same magnitude
  /// as the original value (`number.abs() == (-number).abs()`),
  /// and the opposite sign (`-(number.sign) == (-number).sign`).
  ///
  /// Negating an integer, `-number`, is equivalent to subtracting
  /// it from zero, `0 - number`.
  ///
  /// (Both properties generally also hold for the other type,
  /// but with a few edge case exceptions).
  num operator -();

  /// The remainder of the truncating division of `this` by [other].
  ///
  /// The result `r` of this operation satisfies:
  /// `this == (this ~/ other) * other + r`.
  /// As a consequence, the remainder `r` has the same sign as the divider
  /// `this`.
  ///
  /// The result is an [int], as described by [int.remainder],
  /// if both this number and [other] are integers,
  /// otherwise the result is a [double].
  ///
  /// Example:
  /// ```dart
  /// print(5.remainder(3)); // 2
  /// print(-5.remainder(3)); // -2
  /// print(5.remainder(-3)); // 2
  /// print(-5.remainder(-3)); // -2
  /// ```
  num remainder(num other);

  /// Whether this number is numerically smaller than [other].
  ///
  /// Returns `true` if this number is smaller than [other].
  /// Returns `false` if this number is greater than or equal to [other]
  /// or if either value is a NaN value like [double.nan].
  bool operator <(num other);

  /// Whether this number is numerically smaller than or equal to [other].
  ///
  /// Returns `true` if this number is smaller than or equal to [other].
  /// Returns `false` if this number is greater than [other]
  /// or if either value is a NaN value like [double.nan].
  bool operator <=(num other);

  /// Whether this number is numerically greater than [other].
  ///
  /// Returns `true` if this number is greater than [other].
  /// Returns `false` if this number is smaller than or equal to [other]
  /// or if either value is a NaN value like [double.nan].
  bool operator >(num other);

  /// Whether this number is numerically greater than or equal to [other].
  ///
  /// Returns `true` if this number is greater than or equal to [other].
  /// Returns `false` if this number is smaller than [other]
  /// or if either value is a NaN value like [double.nan].
  bool operator >=(num other);

  /// Whether this number is a Not-a-Number value.
  ///
  /// Is `true` if this number is the [double.nan] value
  /// or any other of the possible [double] NaN values.
  /// Is `false` if this number is an integer,
  /// a finite double or an infinite double ([double.infinity]
  /// or [double.negativeInfinity]).
  ///
  /// All numbers satisfy exactly one of [isInfinite], [isFinite]
  /// and `isNaN`.
  bool get isNaN;

  /// Whether this number is negative.
  ///
  /// A number is negative if it's smaller than zero,
  /// or if it is the double `-0.0`.
  /// This precludes a NaN value like [double.nan] from being negative.
  bool get isNegative;

  /// Whether this number is positive infinity or negative infinity.
  ///
  /// Only satisfied by [double.infinity] and [double.negativeInfinity].
  ///
  /// All numbers satisfy exactly one of `isInfinite`, [isFinite]
  /// and [isNaN].
  bool get isInfinite;

  /// Whether this number is finite.
  ///
  /// The only non-finite numbers are NaN values, positive infinity, and
  /// negative infinity. All integers are finite.
  ///
  /// All numbers satisfy exactly one of [isInfinite], `isFinite`
  /// and [isNaN].
  bool get isFinite;

  /// The absolute value of this number.
  ///
  /// The absolute value is the value itself, if the value is non-negative,
  /// and `-value` if the value is negative.
  ///
  /// Integer overflow may cause the result of `-value` to stay negative.
  ///
  /// ```dart
  /// print((2).abs()); // 2
  /// print((-2.5).abs()); // 2.5
  /// ```
  num abs();

  /// Negative one, zero or positive one depending on the sign and
  /// numerical value of this number.
  ///
  /// The value minus one if this number is less than zero,
  /// plus one if this number is greater than zero,
  /// and zero if this number is equal to zero.
  ///
  /// Returns NaN if this number is a [double] NaN value.
  ///
  /// Returns a number of the same type as this number.
  /// For doubles, `(-0.0).sign` is `-0.0`.
  ///
  /// The result satisfies:
  /// ```dart
  /// n == n.sign * n.abs()
  /// ```
  /// for all numbers `n` (except NaN, because NaN isn't `==` to itself).
  num get sign;

  /// The integer closest to this number.
  ///
  /// Rounds away from zero when there is no closest integer:
  ///  `(3.5).round() == 4` and `(-3.5).round() == -4`.
  ///
  /// The number must be finite (see [isFinite]).
  ///
  /// If the value is greater than the highest representable positive integer,
  /// the result is that highest positive integer.
  /// If the value is smaller than the highest representable negative integer,
  /// the result is that highest negative integer.
  int round();

  /// The greatest integer no greater than this number.
  ///
  /// Rounds fractional values towards negative infinity.
  ///
  /// The number must be finite (see [isFinite]).
  ///
  /// If the value is greater than the highest representable positive integer,
  /// the result is that highest positive integer.
  /// If the value is smaller than the highest representable negative integer,
  /// the result is that highest negative integer.
  int floor();

  /// The least integer no smaller than `this`.
  ///
  /// Rounds fractional values towards positive infinity.
  ///
  /// The number must be finite (see [isFinite]).
  ///
  /// If the value is greater than the highest representable positive integer,
  /// the result is that highest positive integer.
  /// If the value is smaller than the highest representable negative integer,
  /// the result is that highest negative integer.
  int ceil();

  /// The integer obtained by discarding any fractional digits from `this`.
  ///
  /// Rounds fractional values towards zero.
  ///
  /// The number must be finite (see [isFinite]).
  ///
  /// If the value is greater than the highest representable positive integer,
  /// the result is that highest positive integer.
  /// If the value is smaller than the highest representable negative integer,
  /// the result is that highest negative integer.
  int truncate();

  /// The double integer value closest to this value.
  ///
  /// Rounds away from zero when there is no closest integer:
  ///  `(3.5).roundToDouble() == 4` and `(-3.5).roundToDouble() == -4`.
  ///
  /// If this is already an integer valued double, including `-0.0`, or it is a
  /// non-finite double value, the value is returned unmodified.
  ///
  /// For the purpose of rounding, `-0.0` is considered to be below `0.0`,
  /// and `-0.0` is therefore considered closer to negative numbers than `0.0`.
  /// This means that for a value `d` in the range `-0.5 < d < 0.0`,
  /// the result is `-0.0`.
  double roundToDouble();

  /// Returns the greatest double integer value no greater than `this`.
  ///
  /// If this is already an integer valued double, including `-0.0`, or it is a
  /// non-finite double value, the value is returned unmodified.
  ///
  /// For the purpose of rounding, `-0.0` is considered to be below `0.0`.
  /// A number `d` in the range `0.0 < d < 1.0` will return `0.0`.
  double floorToDouble();

  /// Returns the least double integer value no smaller than `this`.
  ///
  /// If this is already an integer valued double, including `-0.0`, or it is a
  /// non-finite double value, the value is returned unmodified.
  ///
  /// For the purpose of rounding, `-0.0` is considered to be below `0.0`.
  /// A number `d` in the range `-1.0 < d < 0.0` will return `-0.0`.
  double ceilToDouble();

  /// Returns the double integer value obtained by discarding any fractional
  /// digits from the double value of `this`.
  ///
  /// If this is already an integer valued double, including `-0.0`, or it is a
  /// non-finite double value, the value is returned unmodified.
  ///
  /// For the purpose of rounding, `-0.0` is considered to be below `0.0`.
  /// A number `d` in the range `-1.0 < d < 0.0` will return `-0.0`, and
  /// in the range `0.0 < d < 1.0` it will return 0.0.
  double truncateToDouble();

  /// Returns this [num] clamped to be in the range [lowerLimit]-[upperLimit].
  ///
  /// The comparison is done using [compareTo] and therefore takes `-0.0` into
  /// account. This also implies that [double.nan] is treated as the maximal
  /// double value.
  ///
  /// The arguments [lowerLimit] and [upperLimit] must form a valid range where
  /// `lowerLimit.compareTo(upperLimit) <= 0`.
  ///
  /// Example:
  /// ```dart
  /// var result = 10.5.clamp(5, 10.0); // 10.0
  /// result = 0.75.clamp(5, 10.0); // 5
  /// result = (-10).clamp(-5, 5.0); // -5
  /// result = (-0.0).clamp(-5, 5.0); // -0.0
  /// ```
  num clamp(num lowerLimit, num upperLimit);

  /// Truncates this [num] to an integer and returns the result as an [int].
  ///
  /// Equivalent to [truncate].
  int toInt();

  /// This number as a [double].
  ///
  /// If an integer number is not precisely representable as a [double],
  /// an approximation is returned.
  double toDouble();

  /// A decimal-point string-representation of this number.
  ///
  /// Converts this number to a [double]
  /// before computing the string representation,
  /// as by [toDouble].
  ///
  /// If the absolute value of `this` is greater than or equal to `10^21`, then
  /// this methods returns an exponential representation computed by
  /// `this.toStringAsExponential()`. Otherwise the result
  /// is the closest string representation with exactly [fractionDigits] digits
  /// after the decimal point. If [fractionDigits] equals 0, then the decimal
  /// point is omitted.
  ///
  /// The parameter [fractionDigits] must be an integer satisfying:
  /// `0 <= fractionDigits <= 20`.
  ///
  /// Examples:
  /// ```dart
  /// 1.toStringAsFixed(3);  // 1.000
  /// (4321.12345678).toStringAsFixed(3);  // 4321.123
  /// (4321.12345678).toStringAsFixed(5);  // 4321.12346
  /// 123456789012345.toStringAsFixed(3);  // 123456789012345.000
  /// 10000000000000000.toStringAsFixed(4); // 10000000000000000.0000
  /// 5.25.toStringAsFixed(0); // 5
  /// ```
  String toStringAsFixed(int fractionDigits);

  /// An exponential string-representation of this number.
  ///
  /// Converts this number to a [double]
  /// before computing the string representation.
  ///
  /// If [fractionDigits] is given, then it must be an integer satisfying:
  /// `0 <= fractionDigits <= 20`. In this case the string contains exactly
  /// [fractionDigits] after the decimal point. Otherwise, without the parameter,
  /// the returned string uses the shortest number of digits that accurately
  /// represent this number.
  ///
  /// If [fractionDigits] equals 0, then the decimal point is omitted.
  /// Examples:
  /// ```dart
  /// 1.toStringAsExponential();       // 1e+0
  /// 1.toStringAsExponential(3);      // 1.000e+0
  /// 123456.toStringAsExponential();  // 1.23456e+5
  /// 123456.toStringAsExponential(3); // 1.235e+5
  /// 123.toStringAsExponential(0);    // 1e+2
  /// ```
  String toStringAsExponential([int? fractionDigits]);

  /// A string representation with [precision] significant digits.
  ///
  /// Converts this number to a [double]
  /// and returns a string representation of that value
  /// with exactly [precision] significant digits.
  ///
  /// The parameter [precision] must be an integer satisfying:
  /// `1 <= precision <= 21`.
  ///
  /// Examples:
  /// ```dart
  /// 1.toStringAsPrecision(2);       // 1.0
  /// 1e15.toStringAsPrecision(3);    // 1.00e+15
  /// 1234567.toStringAsPrecision(3); // 1.23e+6
  /// 1234567.toStringAsPrecision(9); // 1234567.00
  /// 12345678901234567890.toStringAsPrecision(20); // 12345678901234567168
  /// 12345678901234567890.toStringAsPrecision(14); // 1.2345678901235e+19
  /// 0.00000012345.toStringAsPrecision(15); // 1.23450000000000e-7
  /// 0.0000012345.toStringAsPrecision(15);  // 0.00000123450000000000
  /// ```
  String toStringAsPrecision(int precision);

  /// The shortest string that correctly represents this number.
  ///
  /// All [double]s in the range `10^-6` (inclusive) to `10^21` (exclusive)
  /// are converted to their decimal representation with at least one digit
  /// after the decimal point. For all other doubles,
  /// except for special values like `NaN` or `Infinity`, this method returns an
  /// exponential representation (see [toStringAsExponential]).
  ///
  /// Returns `"NaN"` for [double.nan], `"Infinity"` for [double.infinity], and
  /// `"-Infinity"` for [double.negativeInfinity].
  ///
  /// An [int] is converted to a decimal representation with no decimal point.
  ///
  /// Examples:
  /// ```dart
  /// (0.000001).toString();  // "0.000001"
  /// (0.0000001).toString(); // "1e-7"
  /// (111111111111111111111.0).toString();  // "111111111111111110000.0"
  /// (100000000000000000000.0).toString();  // "100000000000000000000.0"
  /// (1000000000000000000000.0).toString(); // "1e+21"
  /// (1111111111111111111111.0).toString(); // "1.1111111111111111e+21"
  /// 1.toString(); // "1"
  /// 111111111111111111111.toString();  // "111111111111111110000"
  /// 100000000000000000000.toString();  // "100000000000000000000"
  /// 1000000000000000000000.toString(); // "1000000000000000000000"
  /// 1111111111111111111111.toString(); // "1111111111111111111111"
  /// 1.234e5.toString();   // 123400
  /// 1234.5e6.toString();  // 1234500000
  /// 12.345e67.toString(); // 1.2345e+68
  /// ```
  /// Note: the conversion may round the output if the returned string
  /// is accurate enough to uniquely identify the input-number.
  /// For example the most precise representation of the [double] `9e59` equals
  /// `"899999999999999918767229449717619953810131273674690656206848"`, but
  /// this method returns the shorter (but still uniquely identifying) `"9e59"`.
  String toString();

  /// Parses a string containing a number literal into a number.
  ///
  /// The method first tries to read the [input] as integer (similar to
  /// [int.parse] without a radix).
  /// If that fails, it tries to parse the [input] as a double (similar to
  /// [double.parse]).
  /// If that fails, too, it invokes [onError] with [input], and the result
  /// of that invocation becomes the result of calling `parse`.
  ///
  /// If no [onError] is supplied, it defaults to a function that throws a
  /// [FormatException].
  ///
  /// For any number `n`, this function satisfies
  /// `identical(n, num.parse(n.toString()))` (except when `n` is a NaN `double`
  /// with a payload).
  ///
  /// The [onError] parameter is deprecated and will be removed.
  /// Instead of `num.parse(string, (string) { ... })`,
  /// you should use `num.tryParse(string) ?? (...)`.
  ///
  /// Examples:
  /// ```dart
  /// var value = num.parse('2021'); // 2021
  /// value = num.parse('3.14'); // 3.14
  /// value = num.parse('  3.14 \xA0'); // 3.14
  /// value = num.parse('0.'); // 0.0
  /// value = num.parse('.0'); // 0.0
  /// value = num.parse('-1.e3'); // -1000.0
  /// value = num.parse('1234E+7'); // 12340000000.0
  /// value = num.parse('+.12e-9'); // 1.2e-10
  /// value = num.parse('-NaN'); // NaN
  /// value = num.parse('0xFF'); // 255
  /// value = num.parse(double.infinity.toString()); // Infinity
  /// value = num.parse('1f'); // Throws.
  /// ```
  static num parse(String input, [@deprecated num onError(String input)?]) {
    num? result = tryParse(input);
    if (result != null) return result;
    if (onError == null) throw FormatException(input);
    return onError(input);
  }

  /// Parses a string containing a number literal into a number.
  ///
  /// Like [parse], except that this function returns `null` for invalid inputs
  /// instead of throwing.
  ///
  /// Examples:
  /// ```dart
  /// var value = num.tryParse('2021'); // 2021
  /// value = num.tryParse('3.14'); // 3.14
  /// value = num.tryParse('  3.14 \xA0'); // 3.14
  /// value = num.tryParse('0.'); // 0.0
  /// value = num.tryParse('.0'); // 0.0
  /// value = num.tryParse('-1.e3'); // -1000.0
  /// value = num.tryParse('1234E+7'); // 12340000000.0
  /// value = num.tryParse('+.12e-9'); // 1.2e-10
  /// value = num.tryParse('-NaN'); // NaN
  /// value = num.tryParse('0xFF'); // 255
  /// value = num.tryParse(double.infinity.toString()); // Infinity
  /// value = num.tryParse('1f'); // null
  /// ```
  static num? tryParse(String input) {
    String source = input.trim();
    // TODO(lrn): Optimize to detect format and result type in one check.
    return int.tryParse(source) ?? double.tryParse(source);
  }
}
