Skip to content

Commit

Permalink
refactory entry code. change parameter value to double
Browse files Browse the repository at this point in the history
  • Loading branch information
sergiotucano committed Mar 26, 2024
1 parent bb5835e commit a601a51
Show file tree
Hide file tree
Showing 6 changed files with 55 additions and 149 deletions.
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,7 @@
## 1.0.0+0
* Refactoring all round code
* BREAK CHANGE, now the value parameter is a double

## 0.0.4+1
* Fix round calc with 3 decimals

Expand Down
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ void main() {
final roundabnt = RoundAbnt();
double resp = 0.00;
resp = roundabnt.roundAbnt('88.241',2); // return 88.24
resp = roundabnt.roundAbnt(88.241,2); // return 88.24
print('$resp');
}
```
12 changes: 6 additions & 6 deletions example/lib/main.dart
Original file line number Diff line number Diff line change
Expand Up @@ -7,22 +7,22 @@ void main() {
final roundabnt = RoundAbnt();

double resp = 0.00;
resp = roundabnt.roundAbnt('88.241',2); /// return 88.24
resp = roundabnt.roundAbnt(88.241,2); /// return 88.24
print('$resp');

resp = roundabnt.roundAbnt('88.248',2); /// return 88.25
resp = roundabnt.roundAbnt(88.248,2); /// return 88.25
print('$resp');

resp = roundabnt.roundAbnt('88.2858',2); /// return 88.29
resp = roundabnt.roundAbnt(88.2858,2); /// return 88.29
print('$resp');

resp = roundabnt.roundAbnt('88.2358',2); /// return 88.24
resp = roundabnt.roundAbnt(88.2358,2); /// return 88.24
print('$resp');

resp = roundabnt.roundAbnt('88.2458',2); /// return 88.25
resp = roundabnt.roundAbnt(88.2458,2); /// return 88.25
print('$resp');

resp = roundabnt.roundAbnt('88.2450',2); /// return 88.24
resp = roundabnt.roundAbnt(88.2450,2); /// return 88.24
print('$resp');

}
182 changes: 42 additions & 140 deletions lib/src/round_abnt.dart
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
import 'package:roundabnt/roundabnt.dart';
import 'dart:math' as math;


/// Regra ABNT :
/// Se o proximo número do último algarismo a ser conservado for menor que 5 :
Expand All @@ -17,157 +19,57 @@ import 'package:roundabnt/roundabnt.dart';
/// https://www.sofazquemsabe.com/2011/01/como-fazer-arredondamento-da-numeracao.html
class RoundAbnt implements RoundAbntImplementation {

//calc rounded number with brazilian abnt rule
@override
double roundAbnt(String aValue, int digits) {
String newValue = '';
String intPart = '0';
String fractPart = '0';
String truncDigit = '0';
String restDigit = '0';
String mantainDigit = '0';
int restValue = 0;
double resultValue = 0.00;

newValue = '';
double roundAbnt(double aValue, int digits, {double delta = 0.00001}) {

try {
///Verify int part. if haven't dot return int part with zero in fract
try {
intPart = aValue.substring(0, aValue.indexOf('.'));
} catch (_) {
intPart = aValue;
truncDigit = '0';
truncDigit = truncDigit + '0' * (digits - truncDigit
.toString()
.length);
newValue = '$intPart.$truncDigit';
resultValue = double.parse(newValue);
return resultValue;
}

///verify fract part
try {
fractPart = aValue.substring(aValue.indexOf('.') + 1);
} catch (_) {
fractPart = '0';
}

if (fractPart.length > 4 && digits < 3){
double tempNumber = roundAbnt(aValue, 3);

try {
intPart = '$tempNumber'.substring(0, '$tempNumber'.indexOf('.'));
} catch (_) {
intPart = '$tempNumber';
truncDigit = '0';
truncDigit = truncDigit + '0' * (digits - truncDigit
.toString()
.length);
newValue = '$intPart.$truncDigit';
resultValue = double.parse(newValue);
return resultValue;
}
// Check if the value is negative
var negativo = (aValue < 0);

// Calculate the power of 10
var pow = math.pow(10, digits.abs());
var powValue = aValue.abs() / 10;
var intValue = powValue.truncate();
var fracValue = powValue - intValue;

powValue = _simpleRoundToEX(fracValue * 10 * pow, -9);
var intCalc = powValue.truncate();
var fracCalc = (fracValue * 100).truncate();

// Apply ABNT rounding rules
if (fracCalc > 50) {
intCalc++;
} else if (fracCalc == 50) {
var lastNumber = (intCalc / 10).truncate() % 10;

if (lastNumber.isOdd) {
intCalc++;
} else {
var restPart = (powValue * 10) % 10;

///verify fract part
String fractTemp = '';
try {
fractTemp = '$tempNumber'.substring('$tempNumber'.indexOf('.') + 1);
} catch (_) {
fractTemp = '0';
if (restPart > delta) intCalc++;
}

fractPart = fractTemp;
}

///calc the digits will be truncade
try {
truncDigit = fractPart.substring(0, digits);
} catch (_) {
truncDigit = fractPart.substring(0);
truncDigit = truncDigit + '0' * (digits - truncDigit
.toString()
.length);
}

///calc the rest digit after de trunc digits
try {
restDigit = fractPart.substring(digits, digits + 1);
} catch (_) {
restDigit = '0';
}

/// calc de digit will be mantained
try {
mantainDigit = fractPart.substring(1, digits);
} catch (_) {
mantainDigit = fractPart.substring(0);
}

restValue = int.parse(restDigit);
resultValue = 0.00;

/// if rest digit < 5 the trunc digit will be maintained
if (restValue < 5) {
newValue = '$intPart.$truncDigit';
resultValue = double.parse(newValue);
} else if (restValue > 5) {
/// if rest digit > 5 the trunc digit sum 1
// Calculate the final rounded value
var result = (intValue * 10 + intCalc / pow);

int addDigit = int.parse(truncDigit) + 1;
// Apply sign to the result if the original value was negative
if (negativo) result = -result;

if (addDigit == 0) {
intPart = '${int.parse(intPart) + 1}';
}

String zeroTemp = digits == 2
? addDigit < 10? '0':''
: addDigit < 100? '0':'';

newValue = '$intPart.$zeroTemp$addDigit';
resultValue = double.parse(newValue);
} else if (restValue == 5) {
/**
* in this case if rest digit == 5
* if is odd sum 1
* if is pair and don't have any 0 sum 1
* if is pair and have any 0 maintain the number
*/

int matainValue = int.parse(mantainDigit);
if ((matainValue % 2) != 0) {
int addDigit = int.parse(truncDigit) + 1;

if (addDigit == 0) {
intPart = '${int.parse(intPart) + 1}';
}

String zeroTemp = digits == 2
? addDigit < 10? '0':''
: addDigit < 100? '0':'';

newValue = '$intPart.$zeroTemp$addDigit';

resultValue = double.parse(newValue);
} else {

int addDigit = int.parse(truncDigit);

String zeroTemp = digits == 2
? addDigit < 10? '0':''
: addDigit < 100? '0':'';

newValue = '$intPart.$zeroTemp$addDigit';

resultValue = double.parse(newValue);
return result;
} catch (_) {
// Return the original number in case of error
return aValue;
}

}
}
}

return resultValue;
}catch(_){
final resul = double.parse(aValue);
return resul;
}
// Function to perform simple rounding with given precision
double _simpleRoundToEX(double value, int digits) {
var shift = math.pow(10, digits.toDouble()).toInt();
return (value * shift).roundToDouble() / shift;
}
}
2 changes: 1 addition & 1 deletion lib/src/round_abnt_implementation.dart
Original file line number Diff line number Diff line change
Expand Up @@ -6,5 +6,5 @@ import 'package:flutter/foundation.dart';
@immutable
abstract class RoundAbntImplementation {
/// call the roundAbnt method
double roundAbnt(String aValue, int digits);
double roundAbnt(double aValue, int digits, {double delta = 0.00001});
}
2 changes: 1 addition & 1 deletion pubspec.yaml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
name: roundabnt
description: This package allow user to round a number with brazilian abnt rule
version: 0.0.4+1
version: 1.0.0+0
homepage: https://github.com/sergiotucano/roundabnt

environment:
Expand Down

0 comments on commit a601a51

Please sign in to comment.