在PHP中对多维数字数组进行排序

I have issues sorting an multidimensional array.

The array looks like:

$array = array(
  array("token" => array(100, 240, 348, 23, 17),
  array("token" => array(293, 28, 283, 2, 28),
  array("token" => array(842, 23, 72, 98, 114)
);

Now I want to sort them by "column". That means, the first column of numbers (100, 293, 842) must be sorted, then the second column (but keeping the first column as it is! It may happen that the columns have the same number with multiple rows) and so on.

Actually I tried this to do with usort(), but this will work only when sorting the first column:

function do_sort($a, $b) {
  $tok_a = $a["token"];
  $tok_b = $b["token"];

  if ($tok_a[0] <= $tok_b[0])
    return false;
  else
    return true;
}

usort($array, "do_sort");

How can I do this? Thanks

Can't you just

foreach ($array as &$item) {
  sort($item['token']);
}

Or have I misunderstood the question?

Here's possible solution:

  1. get rid of 'token', i.e., make 2D array
  2. swap columns and rows (transpose array)
  3. sort each column
  4. swap back columns and rows (get initial structure)
  5. put 'token' back

Code:

function array_transpose(array $array) {
    $result = array();
    foreach ( $array as $rowNum => $row ) {
        foreach ( $row as $colNum => $value ) {
            $result[$colNum][$rowNum] = $value;
        }
    }
    return $result;
}

$array = array(
  array("token" => array(100, 240, 348, 23, 17)),
  array("token" => array(293, 28, 283, 2, 28)),
  array("token" => array(842, 23, 72, 98, 114)),
);

// get rid of 'token'
foreach ( $array as &$item ) {
    $item = $item['token'];
}
unset($item);

// swap columns and rows
$array = array_transpose($array);

// sort columns
foreach ( $array as &$item ) {
    sort($item);
}
unset($item);

// swap back columns and rows
$array = array_transpose($array);

// put 'token' back
foreach ( $array as &$item ) {
    $item = array('token' => $item);
}
unset($item);

// display results
foreach ( $array as $row ) {
    foreach ( $row['token'] as $value ) {
        printf('%-7d', $value);
    }
    echo "
";
}

Output:

100    23     72     2      17     
293    28     283    23     28     
842    240    348    98     114    

I think this will do what you are after. I've made some assumptions here (such as $array is really an array, has at least one sub-array, all sub-arrays have token as the key, and all sub-arrays have the same number of elements).

<?php

$array = array(
  array("token" => array(100, 240, 348, 23, 17)),
  array("token" => array(293, 28, 283, 2, 28)),
  array("token" => array(842, 23, 72, 98, 114)),
);

$count_outer = count($array);
$count_inner = count($array[0]['token']);

for ($i=0; $i < $count_inner; $i++) {
    $temp_arr = array();

    for ($j=0; $j < $count_outer; $j++) {
        $temp_arr[] = $array[$j]['token'][$i];
    }
    sort($temp_arr);

    for ($j=0; $j < $count_outer; $j++) {
        $array[$j]['token'][$i] = $temp_arr[$j];
    }
}

foreach ($array as $value) {
    var_dump($value);
    echo '<br>';
}

Output:

array(1) { ["token"]=> array(5) { [0]=> int(100) [1]=> int(23) [2]=> int(72) [3]=> int(2) [4]=> int(17) } } array(1) { ["token"]=> array(5) { [0]=> int(293) [1]=> int(28) [2]=> int(283) [3]=> int(23) [4]=> int(28) } } array(1) { ["token"]=> array(5) { [0]=> int(842) [1]=> int(240) [2]=> int(348) [3]=> int(98) [4]=> int(114) } }