Doc #62590 [Asn]: usort & al : documentation about callback is wrong

From: Date: Fri, 20 Jul 2012 01:00:12 +0000
Subject: Doc #62590 [Asn]: usort & al : documentation about callback is wrong
References: 1  Groups: php.doc.bugs 
Request: Send a blank email to doc-bugs+get-8587@lists.php.net to get a copy of this message
Edit report at https://bugs.php.net/bug.php?id=62590&edit=1 ID: 62590 Updated by: googleguy@php.net Reported by: fabien dot delorme at gmail dot com Summary: usort & al : documentation about callback is wrong Status: Assigned Type: Documentation Problem Package: Documentation problem Operating System: MacOS lion PHP Version: 5.3.14 Assigned To: googleguy Block user comment: N Private report: N New Comment: The custom callback function should return an integer value either less-than, greater-than, or equal to zero. For less than, greater than, and equal comparison respectively. The documentation is really wrong here as it does explicitly state "an integer". The code in this example is clearly return floating point numbers. What happens is that the last two values in this array (6.17 and 5.76): Actual result: -------------- array(8) { [0]=> float(15.44) [1]=> float(10.43) [2]=> float(8.62) [3]=> float(8.91) [4]=> float(7.21) [5]=> float(6.12) [6]=> float(5.76) [7]=> float(6.17) } are both cast to integer values behind the scenes (from array.c line 592): long retval; convert_to_long_ex(&retval_ptr); retval = Z_LVAL_P(retval_ptr); zval_ptr_dtor(&retval_ptr); return retval < 0 ? -1 : retval > 0 ? 1 : 0; As you can see the comparison is quite similar to the proposed "return $x == $y ? 0 : ($x < $y ? -1 : 1);" you included here. What is really expected here is ($comparison > 0 || $comparison < 0 || $compirson == 0). I will try to make the documentation more clear about this where possible, but for now this is not concerned a documentation bug. I can appreciate a need for further clarification where subtle details may not be too obvious at first. Previous Comments: ------------------------------------------------------------------------ [2012-07-17 19:56:12] fabien dot delorme at gmail dot com Description: ------------ The documentation for usort function (and, it seems, other relative functions, although I haven't tested all of them) is slightly wrong regarding the callback function. It says : "The comparison function must return an integer less than, equal to, or greater than zero if the first argument is considered to be respectively less than, equal to, or greater than the second." However it sometimes results in wrong results if the return value is not precisely -1, 0 or 1. For example, returning $arg2 - $arg1 won't always perform the correct operation. Even if PHP builtin comparison functions all have this behavior (returning precisely -1, 0 or 1), this is not necessarily the case for user-defined functions and either code or documentation should be clear about what values shall be returned. Test script: --------------- $a=array(15.44, 5.76, 10.43, 6.12, 6.17, 7.21, 8.62, 8.91); usort($a, function($x, $y) {return $y - $x; }); var_dump($a); // The above would work if the lambda was something like // function($x, $y) { return $x == $y ? 0 : ($x < $y ? -1 : 1);} Expected result: ---------------- array(8) { [0]=> float(15.44) [1]=> float(10.43) [2]=> float(8.91) [3]=> float(8.62) [4]=> float(7.21) [5]=> float(6.17) [6]=> float(6.12) [7]=> float(5.76) } Actual result: -------------- array(8) { [0]=> float(15.44) [1]=> float(10.43) [2]=> float(8.62) [3]=> float(8.91) [4]=> float(7.21) [5]=> float(6.12) [6]=> float(5.76) [7]=> float(6.17) } ------------------------------------------------------------------------ -- Edit this bug report at https://bugs.php.net/bug.php?id=62590&edit=1

« previous php.doc.bugs (#8587) next »