Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

negative discount for rule leads to floating point error #2559

Open
xprojects-de opened this issue Jan 8, 2025 · 1 comment
Open

negative discount for rule leads to floating point error #2559

xprojects-de opened this issue Jan 8, 2025 · 1 comment

Comments

@xprojects-de
Copy link

xprojects-de commented Jan 8, 2025

Isotope 2.9.6, C4.13, PHP 8.1 and also PHP 8.3

A discount with a negative percentage value will randomly lead to incorrect calculations (see screenshots. 139: wrong, 159 ok)

Bildschirmfoto 2025-01-08 um 14 25 41
Bildschirmfoto 2025-01-08 um 14 26 01

The case here is a product price of 139.00 and a discount of -10% as rule for each Product and normal rounding.
Screenshot 2025-01-08 at 14-44-22 Regeln   Gutscheine Bearbeite die Regel mit der ID 9 bergwerk net

After testing and discussion it seems to be a floating point error for ceil at

$fltPrice = $fltPrice > 0 ? (floor($fltPrice * 100) / 100) : (ceil($fltPrice * 100) / 100);

As @fritzmg said the error can be reproduced using

$fltPrice = (139.0 / 100) * -10.0;

var_dump([
    $fltPrice,
    $fltPrice * 100,
    ceil($fltPrice * 100),
    ceil($fltPrice * 100) / 100,
]);

More test results:

dd at line 205:

dd(
    $fltPrice,
    $fltPrice * 100,
    ceil($fltPrice * 100),
    ceil($fltPrice * 100) / 100,
);

// Result:
^ -13.9
^ -1390.0
^ -1389.0
^ -13.89
^ -13.9
^ -1390.0
^ -1389.0
^ -13.89
@ausi
Copy link

ausi commented Jan 9, 2025

You can round it to the desired precision beforehand (maybe only directly before calling floor or ceil). But it depends on what the code actually wants to have as a result in certain edge cases...

$fltPrice = (139.0 / 100) * -10.0;
$fltPrice = round($fltPrice, 5);

var_dump([
    $fltPrice,
    $fltPrice * 100,
    ceil($fltPrice * 100),
    ceil($fltPrice * 100) / 100,
]);

// array(4) {
//   [0]=>
//   float(-13.9)
//   [1]=>
//   float(-1390)
//   [2]=>
//   float(-1390)
//   [3]=>
//   float(-13.9)
// }

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants