按两个值排列数组

时间:2014-10-07 19:02:29

标签: php arrays sorting

我有以下数组

$q = array(
  array(
    'ID'=>'0',
    'post_date'=>'2014-09-20 20:01:52',
    'post_type'=>'event_type'
  ),
  array(
    'ID'=>'1',
    'post_date'=>'2014-09-13 11:33:10',
    'post_type'=>'post'
  ),
  array(
    'ID'=>'2',
    'post_date'=>'2014-09-11 16:55:32',
    'post_type'=>'cameras'
  ),
  array(
    'ID'=>'3',
    'post_date'=>'2014-09-10 17:44:52',
    'post_type'=>'post'
  ),
    array(
    'ID'=>'4',
    'post_date'=>'2014-09-09 17:44:52',
    'post_type'=>'cameras'
  ),

  array(
    'ID'=>'5',
    'post_date'=>'2014-09-07 15:20:10',
    'post_type'=>'post'
  ),
  array(
    'ID'=>'6',
    'post_date'=>'2014-07-08 20:01:52',
    'post_type'=>'event_type'
  ),
  array(
    'ID'=>'7',
    'post_date'=>'2014-07-06 15:26:28',
    'post_type'=>'cameras'
  ),
  array(
    'ID'=>'8',
    'post_date'=>'2014-06-30 17:44:52',
    'post_type'=>'event_type'
  ),
);

我需要按照我指定的顺序按post_type对其进行排序。订单应为event_type,然后是post,然后是cameras。我可以通过以下代码实现这一点,没问题,

function cmp($a, $b)
{
        if($b['post_type'] == 'event_type') {
            return 1;
        }
        elseif($a['post_type'] == 'event_type') {
            return -1;
        }
        elseif($b['post_type'] == 'post') {
            return 1;
        }
        elseif($a['post_type'] == 'post') {
            return -1;
        }
        elseif($b['post_type'] == 'cameras') {
            return 1;
        }
        elseif($a['post_type'] == 'cameras') {
            return -1;
        }
        return ($a < $b) ? -1 : 1;
}


usort($q, "cmp");

正如我指定的那样,数组按post_type正确排序。我遇到的问题是,这种排序不会使数组按ID排序。让我解释。这是排序后的输出

array(9) {
  [0]=>
  array(3) {
    ["ID"]=>
    string(1) "8"
    ["post_date"]=>
    string(19) "2014-06-30 17:44:52"
    ["post_type"]=>
    string(10) "event_type"
  }
  [1]=>
  array(3) {
    ["ID"]=>
    string(1) "0"
    ["post_date"]=>
    string(19) "2014-09-20 20:01:52"
    ["post_type"]=>
    string(10) "event_type"
  }
  [2]=>
  array(3) {
    ["ID"]=>
    string(1) "6"
    ["post_date"]=>
    string(19) "2014-07-08 20:01:52"
    ["post_type"]=>
    string(10) "event_type"
  }
  [3]=>
  array(3) {
    ["ID"]=>
    string(1) "1"
    ["post_date"]=>
    string(19) "2014-09-13 11:33:10"
    ["post_type"]=>
    string(4) "post"
  }
  [4]=>
  array(3) {
    ["ID"]=>
    string(1) "3"
    ["post_date"]=>
    string(19) "2014-09-10 17:44:52"
    ["post_type"]=>
    string(4) "post"
  }
  [5]=>
  array(3) {
    ["ID"]=>
    string(1) "5"
    ["post_date"]=>
    string(19) "2014-09-07 15:20:10"
    ["post_type"]=>
    string(4) "post"
  }
  [6]=>
  array(3) {
    ["ID"]=>
    string(1) "2"
    ["post_date"]=>
    string(19) "2014-09-11 16:55:32"
    ["post_type"]=>
    string(7) "cameras"
  }
  [7]=>
  array(3) {
    ["ID"]=>
    string(1) "7"
    ["post_date"]=>
    string(19) "2014-07-06 15:26:28"
    ["post_type"]=>
    string(7) "cameras"
  }
  [8]=>
  array(3) {
    ["ID"]=>
    string(1) "4"
    ["post_date"]=>
    string(19) "2014-09-09 17:44:52"
    ["post_type"]=>
    string(7) "cameras"
  }
}

例如,查看event_type的排序方式。它按以下顺序ID8, 0, 6进行排序。我需要它0, 6, 8cameras也是如此。订购后,ID订单为2, 7, 4我需要的地方2, 4, 7

有关如何解决此问题的任何建议?我正确使用usort吗?

1 个答案:

答案 0 :(得分:2)

你应该总是比较回调方法中的两个东西。一旦你在一个元素上达到某个值,你基本上就说“这个更大”:

if($b['post_type'] == 'event_type') {
   return 1;
}

如果两者都是event_type怎么办?你忽略了这一点。

你应该这样做:

function cmp($a, $b)
{
   $types = array (
    'event_type' => 1,
    'post' => 2,
    'cameras' => 3
   );

   $compare1 = $types[$a["post_type"]] - $types[$b["post_type"]];

   if ($compare1 === 0){
     //same category, compare by id.
     return $a["ID"] - $b["ID"];
   }else{
     //different category, save to ignore the id.
     return $compare1;
   }
}

ps:如果它应该是$a-$b$b-$a,那就玩吧 - 我总是搞砸了。