2010-03-19 80 views
80

我有数组以下药结构:PHP排序数组通过子数组值

Array 
     (
      [0] => Array 
       (
        [configuration_id] => 10 
        [id] => 1 
        [optionNumber] => 3 
        [optionActive] => 1 
        [lastUpdated] => 2010-03-17 15:44:12 
       ) 

      [1] => Array 
       (
        [configuration_id] => 9 
        [id] => 1 
        [optionNumber] => 2 
        [optionActive] => 1 
        [lastUpdated] => 2010-03-17 15:44:12 
       ) 

      [2] => Array 
       (
        [configuration_id] => 8 
        [id] => 1 
        [optionNumber] => 1 
        [optionActive] => 1 
        [lastUpdated] => 2010-03-17 15:44:12 
       ) 
    ) 

什么是订单的最佳途径阵列,基于该OPTIONNUMBER增量的方式?

所以结果如下:

Array 
     (
      [0] => Array 
       (
        [configuration_id] => 8 
        [id] => 1 
        [optionNumber] => 1 
        [optionActive] => 1 
        [lastUpdated] => 2010-03-17 15:44:12 
       ) 

      [1] => Array 
       (
        [configuration_id] => 9 
        [id] => 1 
        [optionNumber] => 2 
        [optionActive] => 1 
        [lastUpdated] => 2010-03-17 15:44:12 
       ) 

      [2] => Array 
       (
        [configuration_id] => 10 
        [id] => 1 
        [optionNumber] => 3 
        [optionActive] => 1 
        [lastUpdated] => 2010-03-17 15:44:12 
       ) 
    ) 

回答

152

使用usort

function cmp_by_optionNumber($a, $b) { 
    return $a["optionNumber"] - $b["optionNumber"]; 
} 

... 

usort($array, "cmp_by_optionNumber"); 

在PHP≥5.3,你应该使用一个anonymous function代替:

usort($array, function ($a, $b) { 
    return $a['optionNumber'] - $b['optionNumber']; 
}); 

注意,上面的两个代码假设$a['optionNumber']是一个整数。如果它们是字符串,则使用@St. John Johnson's solution


在PHP≥7.0中,使用spaceship operator <=>而不是减法来防止溢出/截断问题。

usort($array, function ($a, $b) { 
    return $a['optionNumber'] <=> $b['optionNumber']; 
}); 
+1

并没有真正helpe我,usort需要我提供其使用的功能 - 这是比较麻烦的问题,我不能让我的头一轮 – Sjwdavies 2010-03-19 13:15:53

+11

嗯,他刚才给你的功能使用。你将不得不接受,并不总是有一个内置的功能来做你想做的,你必须自己写。比较函数只需要返回1,0或-1,表示两个元素的排序顺序。 – Tesserex 2010-03-19 13:19:08

+1

我进一步研究了usort,它确实很酷。 我写了一个简单的比较函数,但是错过了'=='。 感谢您的帮助 – Sjwdavies 2010-03-19 13:38:09

48

使用usort

usort($array, 'sortByOption'); 
function sortByOption($a, $b) { 
    return strcmp($a['optionNumber'], $b['optionNumber']); 
} 
+0

这个为我工作。 @ KennyTM似乎没有工作 – 2012-06-15 03:35:12

+7

@BenSinclair,这是因为Kenny的解决方案是针对数字的,这个解决方案是针对字符串的。他们都是正确的:-) +1这个选择。 – kubilay 2013-01-29 19:34:59

+0

为我工作,因为我正在排序字符串... – Andy 2013-06-08 03:16:16

4

使用像以上这样的一种功能,当键被除去。如果密钥是很重要的,下面的函数将维持...但foreach循环是非常低效。

function subval_sort($a,$subkey) { 
    foreach($a as $k=>$v) { 
     $b[$k] = strtolower($v[$subkey]); 
    } 
    asort($b); 
    foreach($b as $key=>$val) { 
     $c[$key] = $a[$key]; 
    } 
    return $c; 
} 
$array = subval_sort($array,'optionNumber'); 

如果您希望从高到低,请使用arsort而不是asort。

信用代码:http://www.firsttube.com/read/sorting-a-multi-dimensional-array-with-php/

3

PHP 5.3+

usort($array, function($a,$b){ return $a['optionNumber']-$b['optionNumber'];}); 
11

我通过KennyTMAJ Quick使用这两种解决方案,并用功能,可以使用ASC在这个问题上帮助很多情况下,像或想出了DESC排序或保存键或者如果你有对象作为数组的孩子。

这里是这样的功能:

/** 
* @param array $array 
* @param string $value 
* @param bool $asc - ASC (true) or DESC (false) sorting 
* @param bool $preserveKeys 
* @return array 
* */ 
function sortBySubValue($array, $value, $asc = true, $preserveKeys = false) 
{ 
    if ($preserveKeys) { 
     $c = array(); 
     if (is_object(reset($array))) { 
      foreach ($array as $k => $v) { 
       $b[$k] = strtolower($v->$value); 
      } 
     } else { 
      foreach ($array as $k => $v) { 
       $b[$k] = strtolower($v[$value]); 
      } 
     } 
     $asc ? asort($b) : arsort($b); 
     foreach ($b as $k => $v) { 
      $c[$k] = $array[$k]; 
     } 
     $array = $c; 
    } else { 
     if (is_object(reset($array))) { 
      usort($array, function ($a, $b) use ($value, $asc) { 
       return $a->{$value} == $b->{$value} ? 0 : ($a->{$value} - $b->{$value}) * ($asc ? 1 : -1); 
      }); 
     } else { 
      usort($array, function ($a, $b) use ($value, $asc) { 
       return $a[$value] == $b[$value] ? 0 : ($a[$value] - $b[$value]) * ($asc ? 1 : -1); 
      }); 
     } 
    } 

    return $array; 
} 

用法:

sortBySubValue($array, 'optionNumber', true, false); 

编辑

第一部分可以使用uasort()和functi被重写上会更短:

/** 
* @param array $array 
* @param string $value 
* @param bool $asc - ASC (true) or DESC (false) sorting 
* @param bool $preserveKeys 
* @return array 
* */ 
function sortBySubValue($array, $value, $asc = true, $preserveKeys = false) 
{ 
    if (is_object(reset($array))) { 
     $preserveKeys ? uasort($array, function ($a, $b) use ($value, $asc) { 
      return $a->{$value} == $b->{$value} ? 0 : ($a->{$value} - $b->{$value}) * ($asc ? 1 : -1); 
     }) : usort($array, function ($a, $b) use ($value, $asc) { 
      return $a->{$value} == $b->{$value} ? 0 : ($a->{$value} - $b->{$value}) * ($asc ? 1 : -1); 
     }); 
    } else { 
     $preserveKeys ? uasort($array, function ($a, $b) use ($value, $asc) { 
      return $a[$value] == $b[$value] ? 0 : ($a[$value] - $b[$value]) * ($asc ? 1 : -1); 
     }) : usort($array, function ($a, $b) use ($value, $asc) { 
      return $a[$value] == $b[$value] ? 0 : ($a[$value] - $b[$value]) * ($asc ? 1 : -1); 
     }); 
    } 
    return $array; 
} 
+0

这是这里最好最有用的答案,应该在最上面;) – 2015-04-07 12:16:42

+0

@EdiBudimilic谢谢你,我欣赏它!顺便说一下,我已经更新了我的答案,并添加了此功能的更短版本:) – 2015-04-07 21:15:22

+1

为了让我为此工作,在比较'$时不得不使用'>'(大于)而不是'-'因为我在比较字符串,所以有'a'和'$ b'值。虽然仍然有效。 – James 2015-11-13 15:19:58