达特银行家的四舍五入

时间:2019-09-10 20:17:53

标签: dart double precision

任何人都可以在Dart中帮助银行家进行四舍五入吗

所以我绕了3 d.p.到最近的2 d.p.除中间的数字外,数字除最近的偶数

例如

print(1.011.toStringAsFixed(2)); // rounds down to 1.01
print(1.019.toStringAsFixed(2)); // rounds up to 1.02
print(1.015.toStringAsFixed(2)); // rounds down to 1.01 but i want up to 1.02
print(1.025.toStringAsFixed(2)); // rounds down to 1.02

2 个答案:

答案 0 :(得分:2)

我有相同的要求,所以我建立了一个。

banker_rounding.dart

import 'dart:math';

import 'package:decimal/decimal.dart';

Decimal _getDecimalOfNumber(Decimal number, int fractionDigits) => number - (number.floor());

Decimal _pow10(int powNum) => Decimal.parse(pow(10, powNum).toString());

Decimal _carryLatest(Decimal number) {
  int decimalLength = number.toString().length - 2;
  Decimal offset = _pow10(-decimalLength);
  return number + offset;
}

Decimal bankerRound(Decimal value, int fractionDigits) {
  // integer of number
  Decimal integerOfNumber = value.floor();
  // decimal of number
  Decimal decimalOfNumber = _getDecimalOfNumber(value, fractionDigits);
  // remain flag
  int remainFlag = (decimalOfNumber * _pow10(fractionDigits + 1) % Decimal.fromInt(10)).toInt();
  Decimal finalMultiple = _pow10(fractionDigits);
  Decimal finalDecimalOfNumber = ((decimalOfNumber * finalMultiple).floor() / finalMultiple);
  if (remainFlag <= 4) {
    // do nothing
  } else if (remainFlag >= 6) {
    // carry
    finalDecimalOfNumber = _carryLatest(finalDecimalOfNumber);
  } else {
    // check bottom has number
    bool hasBottom = _getDecimalOfNumber(decimalOfNumber * _pow10(fractionDigits + 1), fractionDigits) != Decimal.zero;
    if (hasBottom) {
      // carry
      finalDecimalOfNumber = _carryLatest(finalDecimalOfNumber);
    } else {
      // check pre remain flag
      int preLastNumber = (decimalOfNumber * _pow10(fractionDigits) % Decimal.fromInt(10)).toInt();
      if (preLastNumber.isOdd) {
        // carry
        finalDecimalOfNumber = _carryLatest(finalDecimalOfNumber);
      } else {
        // do nothing
      }
    }
  }
  return integerOfNumber + finalDecimalOfNumber;
}

答案 1 :(得分:0)

这里是经过测试的银行家四舍五入算法。 对于十进制(100%准确):

import 'dart:math';

import 'package:decimal/decimal.dart';

var _halfDec = Decimal.parse('0.5');
Decimal bankerRoundDecimal(Decimal value) {
  var rounded = value.round();
  if(rounded - value == _halfDec)
    if(value.ceil().toInt() % 2 != 0)
      rounded = value.floor();

  return rounded;
}

并加倍:

double bankerRound(double value) {
  var rounded = value.roundToDouble();
  if(((rounded - value) * 100).round() == 50)
    if(value.ceil() % 2 != 0)
      rounded = value.floorToDouble();

  return rounded;
}