当前位置: 动力学知识库 > 问答 > 编程问答 >

php - Floating point test assertion - why do these "identical" arrays fail?

问题描述:

I'm using assertSame() in PHPUnit to compare a database result with expected values. The results are floating point numbers.

PHPUnit returns this message (but I can't spot any differences):

Failed asserting that Array (

'1_1' => 11.111111111111

'1_2' => 33.333333333333

'1_3' => 55.555555555556

'1_4' => 0.0

'1_5' => null

'1_total' => 100.0

) is identical to Array (

'1_1' => 11.111111111111

'1_2' => 33.333333333333

'1_3' => 55.555555555556

'1_4' => 0.0

'1_5' => null

'1_total' => 100.0

)

Why is this failing and what is the correct way to compare an arrays of floating point values?

网友答案:

assertEquals has a $floating_delta argument for this type of cases:

$this->assertEquals($expected_array, $actual_array, '', 0.00001);

PHPUnit docs

网友答案:

The problem is almost certainly floating point precision. In the print_r, only so many digits are shown. If all significant bits were displayed, the situation is probably something like this:

Failed asserting that Array (
    '1_1' => 11.1111111111110347
    '1_2' => 33.3333333333331678
    '1_3' => 55.5555555555562773
    '1_4' => 0.0
    '1_5' => null
    '1_total' => 100.0
) is identical to Array (
    '1_1' => 11.1111111111110346
    '1_2' => 33.3333333333331679
    '1_3' => 55.5555555555562771
    '1_4' => 0.0
    '1_5' => null
    '1_total' => 100.0
)

Every floating point comparison—especially equality—must consider the lack of infinite precision.

if ($var == 0.005)     /* just plain wrong! */

if (abs ($var, 0.005) < 0.001)    /*  more correct  */

if (abs ($var, 0.005) < 0.0001)    /* maybe more correct, depending on application */

if (abs ($var, 0.005) < 0.0000001)    /* possibly more appropriate */
网友答案:

Unless anyone has a better suggestion, I will assume this is a floating point precision error, and follow the PHP manual advice: do not compare floating point numbers directly for equality.

So my own solution is to round the array values before comparison.

分享给朋友:
您可能感兴趣的文章:
随机阅读: