PHP - Sort multi-dimensional array by another array

Solution 1:

In your example the ids in the $data array are are numbered consecutively and starting at 1. The code I give below assumes this is always the case. If this is not the case, the code does not work.

$result = array();
$index = 0;
foreach ($order as $position) {
    $result[$index] = $data[$position - 1];
    $index++;
}

At http://codepad.org/YC8w0yHh you can see that it works for your example data.

EDIT

If the assumption mentioned above does not hold, the following code will achieve the same result:

<?php

$data = array(
    array('id' => 1, 'title' => 'whatever'),
    array('id' => 2, 'title' => 'whatever'),
    array('id' => 3, 'title' => 'whatever')
);

$order = array(2,3,1);
$order = array_flip($order);

function cmp($a, $b)
{
    global $order;

    $posA = $order[$a['id']];
    $posB = $order[$b['id']];

    if ($posA == $posB) {
        return 0;
    }
    return ($posA < $posB) ? -1 : 1;
}

usort($data, 'cmp');

var_dump($data);

See http://codepad.org/Q7EcTSfs for proof.

By calling array_flip() on the $order array it can be used for position lookup. This is like a hashtable lookup, which is linear in time, or O(n). You cannot do better.

Solution 2:

There is no built-in function for this in PHP and i am unable to think of any custom function, which would do this using usort. But array_map is simple enough, imo, so why not use it instead?

$sorted = array_map(function($v) use ($data) {
    return $data[$v - 1];
}, $order);