2013-01-25 132 views
0

我想按以下順序按多個鍵對以下數組排序:首先按「type」,然後「product」,最後按「name」。這很容易用usort完成,儘管我的客戶希望「產品」按特定順序排序:訂書機,活頁夾,書本。按一定順序按多個鍵對數組排序

$arr = array(
    array(
     'type' => 'School', 
     'product' => 'Book', 
     'name' => 'My book', 
     'data' => '...' 
    ), 
    array(
     'type' => 'Job', 
     'product' => 'Stapler', 
     'name' => 'My stapler', 
     'data' => '...' 
    ), 
    array(
     'type' => 'Personal', 
     'product' => 'Binder', 
     'name' => 'My binder', 
     'data' => '...' 
    ), 
    array(
     'type' => 'School', 
     'product' => 'Book', 
     'name' => 'My book', 
     'data' => '...' 
    ) 
); 

有誰知道一個聰明的方式來做到這一點?

+0

你想是這樣的array( 'type' => 'School', 'type' => 'Job', 'type' => 'Personal' )

回答

1
usort($arr, function ($a, $b) { 
    // by type 
    $r = strcmp($a['type'], $b['type']); 
    if ($r !== 0) { 
    return $r; 
    } 

    // by product 
    // note: one might want to check if `$a/$b['product']` really is in `$order` 
    $order = array('Stapler', 'Binder', 'Book'); 
    $r = array_search($a['product'], $order) - array_search($b['product'], $order); 
    if ($r !== 0) { 
    return $r; 
    } 

    // or similar, with a little help by @fab ;) 
    /* 
    $order = array('Stapler' => 0, 'Binder' => 1, 'Book' => 2); 
    $r = $order[$a['product']] - $order[$b['product']]; 
    if ($r !== 0) { 
    return $r; 
    } 
    */ 

    // name 
    return strcmp($a['name'], $b['name']); 
}); 
+0

好極了!謝謝。 – frigg

1

usort不會限制你這樣做。我假設你的問題是如何比較排序回調函數中的product值。這可以用地圖來完成,如:

$mapProductOrder = array_flip(array('Stapler', 'Binder', 'Book')); 
// same as: array('Stapler' => 0, 'Binder' => 1, 'Book' => 2) 

比較$item1$item2使用:

$mapProductOrder[$item1['product']] < $mapProductOrder[$item2['product']]