# Sorting Bug / Wrong behavior?

- Thread: https://externals.io/message/11584
- Original archive: https://news-web.php.net/php.internals/11584
- Started by John Coggeshall on 2004-07-27T19:48:28+00:00
- Messages: 14
- Reply by email to internals@lists.php.net
- More for agents: search with https://externals.io/search.md?q={query} · JSON API at https://externals.io/api · documentation at https://externals.io/llms.txt

---

## #11584 — John Coggeshall — 2004-07-27T19:48:28+00:00

URL: https://externals.io/message/11584#11584

Consider the following:

<?php $a = array('a', 'b', 'c', 'a'=>0, 'b'=>1, 'c'=>2);
      sort($a);
      print_r($a);
?>

This produces a bogus output:

Array
(
    [0] => a
    [1] => b
    [2] => 0
    [3] => c
    [4] => 1
    [5] => 2
)


Notice how 0 and c are switched incorrectly. Attached is a patch to 
zend_operators.c that fixes it.

---

## #11586 — Stefan Walk — 2004-07-27T20:08:47+00:00

URL: https://externals.io/message/11584#11586 · In reply to: #11584

> Notice how 0 and c are switched incorrectly. Attached is a patch to 
> zend_operators.c that fixes it. 

The Manual says:

> Warning
> 
> Be carefull when sorting arrays with mixed types values because `sort()`
> can produce unpredictable results.

You could use SORT_STRING, natsort, etc...

If this gets "fixed", the $a = "0d9"; var_dump(++$a, ++$a); thing could
also be "fixed", as its WTF factor is as high... or "010" == "1e1" being
true. It's all the consequence of PHPs handling with numbers and
strings, which can produce results that strike you as odd.

---

## #11588 — Andi Gutmans — 2004-07-28T06:19:06+00:00

URL: https://externals.io/message/11584#11588 · In reply to: #11584

This isn't a bug. All those strings evaluate to 0.
You should use a `sort()` function which is suitable.

At 02:48 PM 7/27/2004 -0500, John Coggeshall wrote:

>Consider the following:
>
><?php $a = array('a', 'b', 'c', 'a'=>0, 'b'=>1, 'c'=>2);
>       sort($a);
>       print_r($a);
>?>
>
>This produces a bogus output:
>
>Array
>(
>     [0] => a
>     [1] => b
>     [2] => 0
>     [3] => c
>     [4] => 1
>     [5] => 2
>)
>
>
>Notice how 0 and c are switched incorrectly. Attached is a patch to
>zend_operators.c that fixes it.

---

## #11651 — Andi Gutmans — 2004-07-30T06:20:46+00:00

URL: https://externals.io/message/11584#11651 · In reply to: #11584

I talked to John about this yesterday. I'll take a closer look at this 
within the coming days to see if this makes sense and how it affects BC in 
general (if at all).

At 09:45 PM 7/27/2004 +0200, Marcus Boerger wrote:
>Hello John,
>
>Tuesday, July 27, 2004, 9:48:28 PM, you wrote:
>
>
> > […]
>
> > […]
>?>>
>
> > […]
>
> > […]
>
>
> > […]
>
>
>The current order simply makes no sense at all.´The following though would:
>0 a b c 1 2   // zero dirst, then strings then numbers
>a b c 0 1 2   // strings first, then numbers
>0 1 2 a b c   // numbers first, then strings
>
>and btw, john you forgot the patch, it is attached here.
>The one provided does the 2nd which means we only ensured
>0 is treated un the same way other numbers are.
>
>Best regards,
>  Marcus                            mailto:helly@php.net

---

## #11654 — Andrey Hristov — 2004-07-30T09:30:18+00:00

URL: https://externals.io/message/11584#11654 · In reply to: #11651

Andi Gutmans wrote:
> I talked to John about this yesterday. I'll take a closer look at this 
> within the coming days to see if this makes sense and how it affects BC 
> in general (if at all).
> 
Can you take a look also at http://bugs.php.net/bug.php?id=29421

thanks,
andrey

---

## #11738 — Andi Gutmans — 2004-07-30T22:39:19+00:00

URL: https://externals.io/message/11584#11738 · In reply to: #11584

How would you expect the sort function to behave on the following:
array(true, false, 0, 1)?
It is a different way of looking at the same problem and you are likely to 
hit this anytime you start comparing/sorting different data types.
In general, I don't think it makes very much sense to fix the comparison 
operator for these special cases.
PHP has always done this kind of type juggling and you would be changing a 
lot of its behavior.
I suggest that when you do try and sort an array with different kind of 
data you define your own sorting callback function.
Making special cases for each such case in the compare function will not 
only change behavior but it will slow down the already "too big for my 
taste" compare function.
I know it's not the answer John was hoping for (I promised him to look into 
it more deeply when I'm back from OSCON) but after doing so and thinking 
about it, I think we'd be going in a direction which wouldn't be good.
I have a feeling this might also not give you the expected behavior for 
something like array(0, "-1") but I haven't actually ran it.

Andi

At 09:45 PM 7/27/2004 +0200, Marcus Boerger wrote:
>Hello John,
>
>Tuesday, July 27, 2004, 9:48:28 PM, you wrote:
>
>
> > […]
>
> > […]
>?>>
>
> > […]
>
> > […]
>
>
> > […]
>
>
>The current order simply makes no sense at all.´The following though would:
>0 a b c 1 2   // zero dirst, then strings then numbers
>a b c 0 1 2   // strings first, then numbers
>0 1 2 a b c   // numbers first, then strings
>
>and btw, john you forgot the patch, it is attached here.
>The one provided does the 2nd which means we only ensured
>0 is treated un the same way other numbers are.
>
>Best regards,
>  Marcus                            mailto:helly@php.net

---

## #12074 — Marcus Boerger — 2004-08-10T18:48:18+00:00

URL: https://externals.io/message/11584#12074 · In reply to: #11654

Hello Andrey,

Friday, July 30, 2004, 11:30:18 AM, you wrote:

> Andi Gutmans wrote:
> > […]
> Can you take a look also at http://bugs.php.net/bug.php?id=29421

We don't affect those. We simply correct the sorting to something
understandable when it comes to edge cases with zero. We don't touch
any other automatic typeconversion related behavior as mentioned in
that but.

php -r 'var_dump(array_search("baz",array("foo",TRUE ,"bar")));'

The above returns int(1) because

php -r 'var_dump((bool)"baz");'

returns bool(true).

Maybe we need a builtin search function that uses idetentity comparison?

regards
marcus

---

## #12077 — Sterling Hughes — 2004-08-10T19:19:33+00:00

URL: https://externals.io/message/11584#12077 · In reply to: #11738

i don't think `sort()` should be changed - this is how php works, for
better or sometimes worse, changing it any other way would break BC,
and it doesn't make much sense.

-Sterling


> How would you expect the sort function to behave on the following:
> array(true, false, 0, 1)?
> It is a different way of looking at the same problem and you are likely to
> hit this anytime you start comparing/sorting different data types.
> In general, I don't think it makes very much sense to fix the comparison
> operator for these special cases.
> PHP has always done this kind of type juggling and you would be changing a
> lot of its behavior.
> I suggest that when you do try and sort an array with different kind of
> data you define your own sorting callback function.
> Making special cases for each such case in the compare function will not
> only change behavior but it will slow down the already "too big for my
> taste" compare function.
> I know it's not the answer John was hoping for (I promised him to look into
> it more deeply when I'm back from OSCON) but after doing so and thinking
> about it, I think we'd be going in a direction which wouldn't be good.
> I have a feeling this might also not give you the expected behavior for
> something like array(0, "-1") but I haven't actually ran it.
> 
> Andi
> 
> 
> 
> At 09:45 PM 7/27/2004 +0200, Marcus Boerger wrote:
> > […]

---

## #12078 — John Coggeshall — 2004-08-10T19:29:18+00:00

URL: https://externals.io/message/11584#12078 · In reply to: #12077

I didn't realize that completely inconsistent behavior was no longer
considered a bug, and this edge case is certainly inconsistent with the
behavior of any other set of values sorted. Using the BC reasoning when
something is broken (i.e. it's not a bug, its a "feature") makes even
less sense.

John


> i don't think `sort()` should be changed - this is how php works, for
> better or sometimes worse, changing it any other way would break BC,
> and it doesn't make much sense.
> 
> -Sterling
> 
> 
> > […]

---

## #12079 — Marcus Boerger — 2004-08-10T19:32:54+00:00

URL: https://externals.io/message/11584#12079 · In reply to: #12077

Hello Sterling,

Tuesday, August 10, 2004, 9:19:33 PM, you wrote:

> i don't think `sort()` should be changed - this is how php works, for
> better or sometimes worse, changing it any other way would break BC,
> and it doesn't make much sense.

Yep, meanwhile i think that if at all we could privide a 'nice' comparison
function inside ext/standard.

marcus

---

## #12081 — Rasmus Lerdorf — 2004-08-10T19:59:09+00:00

URL: https://externals.io/message/11584#12081 · In reply to: #12077

> i don't think `sort()` should be changed - this is how php works, for
> better or sometimes worse, changing it any other way would break BC,
> and it doesn't make much sense.

I agree that we should keep the generic sort function the same.  Might be
nice to add some more sort flags though.  It's somewhat annoying that the
sort_string sort option doesn't use strcoll, for example, so you have to
use a usort to get proper string sorting in most languages.

-Rasmus

---

## #12084 — Sterling Hughes — 2004-08-10T20:16:11+00:00

URL: https://externals.io/message/11584#12084 · In reply to: #12081

no argument there, having a few more reasonable sort options/methods
makes sense to me, so long as they offer new functionality (as opposed
to fixing an "inconsistency") and don't affect the default
behaviour...

-sterling


> 
> > […]
> 
> I agree that we should keep the generic sort function the same.  Might be
> nice to add some more sort flags though.  It's somewhat annoying that the
> sort_string sort option doesn't use strcoll, for example, so you have to
> use a usort to get proper string sorting in most languages.
> 
> -Rasmus

---

## #12085 — John Coggeshall — 2004-08-10T20:47:44+00:00

URL: https://externals.io/message/11584#12085 · In reply to: #12081

Which generic sort function? They all use the same sorting code as far
as I can tell.

John


> 
> > […]
> 
> I agree that we should keep the generic sort function the same.  Might be
> nice to add some more sort flags though.  It's somewhat annoying that the
> sort_string sort option doesn't use strcoll, for example, so you have to
> use a usort to get proper string sorting in most languages.
> 
> -Rasmus

---

## #12082 — Andrey Hristov — 2004-08-10T22:01:58+00:00

URL: https://externals.io/message/11584#12082 · In reply to: #12074

Marcus Boerger wrote:
> Hello Andrey,
> 
> > […]
> 
> 
> We don't affect those. We simply correct the sorting to something
> understandable when it comes to edge cases with zero. We don't touch
> any other automatic typeconversion related behavior as mentioned in
> that but.
> 
> php -r 'var_dump(array_search("baz",array("foo",TRUE ,"bar")));'
> 
> The above returns int(1) because
> 
> php -r 'var_dump((bool)"baz");'
> 
> returns bool(true).
> 
> Maybe we need a builtin search function that uses idetentity comparison?

Ugh? What kind of comparison?

> regards
> marcus
> 

thanks
andrey
