1

Is the sorting function on Laravel 5 Eloquent collections a stable sort? A stable sort will not reorder elements with equal sort key.

That is, given this input list:

| order | value |
|-------+-------|
| 5     | a     |
| 2     | b     |
| 5     | c     |
| 10    | d     |

Can I expect $list->sortBy('order') to always return the following result?

| order | value |
|-------+-------|
| 2     | b     |
| 5     | a     | <-- a and c have not
| 5     | c     | <-- switched places
| 10    | d     |
Emil Vikström
  • 90,431
  • 16
  • 141
  • 175

1 Answers1

4

The source code can be found in Illuminate/Support/Collection.php:

public function sortBy($callback, $options = SORT_REGULAR, $descending = false)
{
    $results = [];
    if ( ! $this->useAsCallable($callback))
    {
        $callback = $this->valueRetriever($callback);
    }
    // First we will loop through the items and get the comparator from a callback
    // function which we were given. Then, we will sort the returned values and
    // and grab the corresponding values for the sorted keys from this array.
    foreach ($this->items as $key => $value)
    {
        $results[$key] = $callback($value, $key);
    }
    $descending ? arsort($results, $options)
                : asort($results, $options);
    // Once we have sorted all of the keys in the array, we will loop through them
    // and grab the corresponding model so we can set the underlying items list
    // to the sorted version. Then we'll just return the collection instance.
    foreach (array_keys($results) as $key)
    {
        $results[$key] = $this->items[$key];
    }
    $this->items = $results;
    return $this;
}

Since the sort() family isn't stable, this function won't be stable either.

There are stable PHP sort functions, but if you want to use them you'll need to patch Laravel.

Community
  • 1
  • 1
  • Hm, too bad. And there is no native sort option for a stable sort either. – Emil Vikström Jun 01 '15 at 12:44
  • 1
    @EmilVikström nope - I found stable PHP sort functions and added them, but you'd have to patch Laravel if you want to use them. –  Jun 01 '15 at 12:44