php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Request #66959 bcadd with floats fails
Submitted: 2014-03-26 12:08 UTC Modified: 2017-09-07 22:42 UTC
Votes:2
Avg. Score:4.0 ± 1.0
Reproduced:1 of 2 (50.0%)
Same Version:0 (0.0%)
Same OS:0 (0.0%)
From: james dot turner dot phpninja at gmail dot com Assigned:
Status: Verified Package: BC math related
PHP Version: 5.5.10 OS: Ubuntu 13
Private report: No CVE-ID: None
View Add Comment Developer Edit
Welcome! If you don't have a Git account, you can't do anything here.
You can add a comment by following this link or if you reported this bug, you can edit this bug over here.
(description)
Block user comment
Status: Assign to:
Package:
Bug Type:
Summary:
From: james dot turner dot phpninja at gmail dot com
New email:
PHP Version: OS:

 

 [2014-03-26 12:08 UTC] james dot turner dot phpninja at gmail dot com
Description:
------------
bcadd does not appear to work for certain numbers when using floats as inputs rather than strings.

This is particularly apparent if you json_decode from json to php variables where floats are generated as you get floats not strings. Any attempt at casting to a string produces the same output.

I can only assume it's actually an issue with float->string casting.

Test script:
---------------
$a = -0.05648055;
$b = -0.00000545;

$c = bcadd($a,$b,9);
$d = $a+$b;

echo $c; // => -0.05648055  <- WRONG
echo $d; // => -0.056486    <- CORRECT

assert($c == -0.056486);

Expected result:
----------------
assert ok

Usage of string literals for the negative floats works fine. However casting the floats to strings fails (which is why I assume that bcadd also has the same problem in casting to strings before computation).

Actual result:
--------------
assert fail

Patches

Add a Patch

Pull Requests

Add a Pull Request

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2014-04-01 13:17 UTC] bwoebi@php.net
-Status: Open +Status: Verified
 [2014-04-01 13:17 UTC] bwoebi@php.net
Actually the bcmath extension doesn't like scientific notation.

var_dump((string)-0.00000545);
string(8) "-5.45E-6"

and 

var_dump(bcadd("-0.05648055","-5.45E-6",9));
string(12) "-0.056480550"

------------

Would be great if someone could make bcmath support scientific notation...
 [2014-04-01 13:47 UTC] nikic@php.net
-Package: *Math Functions +Package: BC math related
 [2014-04-01 13:47 UTC] nikic@php.net
BCMath explicitly works with strings, not floating point numbers. In https://bugs.php.net/bug.php?id=55160 Mike made the decision that we should not have extra support for passing floats to bc functions.
 [2014-04-02 21:56 UTC] trainmaster at gmx dot net
@nikic

See bwoebi's example when string arguments are passed. The problem seems to be the scientific notation.
 [2014-04-02 22:04 UTC] trainmaster at gmx dot net
Some more examples (Output for 5.2.2 - 5.6.0alpha3):

var_dump(bcadd(0,-0.00555555,9));
// string(12) "-0.005555550"
var_dump((string) -0.00555555);
// string(11) "-0.00555555"

var_dump(bcadd(0,-0.00055555,9));
// string(12) "-0.000555550"
var_dump((string) -0.00055555);
// string(11) "-0.00055555"

var_dump(bcadd(0,-0.00005555,9));
// string(11) "0.000000000"
var_dump((string) -0.00005555);
// string(10) "-5.555E-05"

var_dump(bcadd(0,-0.00000555,9));
// string(11) "0.000000000"
var_dump((string) -0.00000555);
// string(9) "-5.55E-06"

var_dump(bcadd(0,-0.00000055,9));
// string(11) "0.000000000"
var_dump((string) -0.00000055);
// string(8) "-5.5E-07"

var_dump(bcadd(0,-0.00000005,9));
// string(11) "0.000000000"
var_dump((string) -0.00000005);
// string(6) "-5E-08"
 [2016-07-13 23:46 UTC] cmb@php.net
> Would be great if someone could make bcmath support scientific
> notation...

There would still be the issue that the string cast depends on the
locale, e.g.

  <?php
  setlocale(LC_NUMERIC, 'de_DE.UTF-8');
  // ...
  var_dump(bcadd(-0.05648055, -0.05648055, 8));

outputs

  string(10) "0.00000000"
 [2016-08-05 22:41 UTC] kalle@php.net
-Type: Bug +Type: Feature/Change Request
 [2017-09-07 22:42 UTC] cmb@php.net
This issue is now documented at least.[1]

Anyhow, I am not sure whether floats should explicitly supported
as BCMath operands, since these are not arbitrary precision
values, and it is unclear what their scale would be. Instead we
may consider to introduce bcinit($number[, $scale]) which would
use the given or default scale to return a respective string.
Furthermore, bcinit() might be helpful if we ever consider to turn
BCMath numbers into objects (what might result in quite
considerable performance improvements, due to fewer necessary type
conversions).

[1] <http://svn.php.net/viewvc?view=revision&revision=343020>
 
PHP Copyright © 2001-2019 The PHP Group
All rights reserved.
Last updated: Sat Dec 07 09:01:24 2019 UTC