Asked  7 Months ago    Answers:  5   Viewed   39 times

I've an array like this

Array (
 [0] => Array( "destination" => "Sydney",
               "airlines" => "airline_1",
               "one_way_fare" => 100,
               "return_fare => 300
       ),
 [2] => Array( "destination" => "Sydney",
               "airlines" => "airline_2",
               "one_way_fare" => 150,
               "return_fare => 350
       ),
 [3] => Array( "destination" => "Sydney",
               "airlines" => "airline_3",
               "one_way_fare" => 180,
               "return_fare => 380
       )
)

How can i sort the value by return_fare asc , one_way_fare asc ?

I tried array_multisort() but i ended up getting mixed up data..

asort only works for one dimensional array, i need to sort by two values or more, how can i achieve this like in SQL, order by field1 asc,field2 asc ?

 Answers

11

array_multisort() is the correct function, you must have messed up somehow:

// Obtain a list of columns
foreach ($data as $key => $row) {
    $return_fare[$key]  = $row['return_fare'];
    $one_way_fare[$key] = $row['one_way_fare'];
}

// Sort the data with volume descending, edition ascending
array_multisort($return_fare, SORT_ASC, $one_way_fare, SORT_ASC, $data);

If you take a look at the comments at PHP's manual page for array_multisort(), you can find a very helpful array_orderby() function which allows you to shorten the above to just this:

$sorted = array_orderby($data, 'return_fare', SORT_ASC, 'one_way_fare', SORT_ASC);

To avoid the looping use array_column() (as of PHP 5.5.0):

array_multisort(array_column($data, 'return_fare'),  SORT_ASC,
                array_column($data, 'one_way_fare'), SORT_ASC,
                $data);
Wednesday, March 31, 2021
 
hjalpmig
answered 7 Months ago
25

I've used a few things here, the main thing is that I use the sorting array as a target for an array_replace() and I use array_column() to index the objects by (this needs PHP 7.0+ to work with objects)...

$input = array_column($inputArray, null, "id");   
$sort = array_fill_keys($sortingArray, null);
$output = array_filter(array_replace($sort, $input));

The array_filter() will remove any elements which aren't in the input array but in the sorting array. The array_fill_keys() is used instead of array_flip() so that I can set a null value, which allows the filter to work.

Wednesday, March 31, 2021
 
aslum
answered 7 Months ago
15

You just need to change your callback function to return negative, zero or positive numbers depending on the values present (or not) in the two items being compared at any one time; just as you would when comparing a single array index in both items.

function callback($a, $b) {
    // Both have [5] so sort by that
    if ($a[5] !== '-' && $b[5] !== '-')
        return $b[5] - $a[5];

    // Neither have [5] so sort by [4]
    if ($a[5] === '-' && $b[5] === '-')
        return $b[4] - $a[4];

    // One has a [5] value
    if ($a[5] === '-')
        return 1;
    else
        return -1;
}
uasort($array, 'callback');
print_r($array);

In this particular case, the above callback could be whittled down to something like:

function callback($a, $b) {
    // Neither have [5] so sort by [4]
    if ($a[5] === '-' && $b[5] === '-')
        return $b[4] - $a[4];

    // One, or both, has a [5] value
    return $b[5] - $a[5];
}
Saturday, May 29, 2021
 
keisar
answered 5 Months ago
26

Use usort which is built explicitly for this purpose.

function cmp($a, $b)
{
    return strcmp($a["title"], $b["title"]);
}

usort($array, "cmp");
Thursday, June 10, 2021
 
Axalix
answered 5 Months ago
50

here an array_multisort example:

foreach ($array as $key => $node) {
   $timestamps[$key]    = $node[2];
}
array_multisort($timestamps, SORT_ASC, $array);
Tuesday, August 3, 2021
 
ALH
answered 3 Months ago
ALH
Only authorized users can answer the question. Please sign in first, or register a free account.
Not the answer you're looking for? Browse other questions tagged :