时间:2011-10-26 16:13:45

标签: php arrays sorting

我有一个包含这种格式字符串的数组:

[0] => "title|url|score|user|date"
[1] => "title|url|score|user|date"
[2] => "title|url|score|user|date"
[3] => "title|url|score|user|date"
...

score字段是一个并不总是唯一的int(例如,多个条目的得分为0)。我希望根据score值对这个数组中的字符串进行排序。最初,我尝试迭代数组并使用与投票得分对应的键创建一个新数组。我很快意识到你不能在数组中有重复的键。

这样做有一个很好的干净方法吗?

6 个答案:

答案 0 :(得分:2)

查看PHP的usort函数

function score_sort($rec1, $rec2)
{
  return $rec1['score'] - $rec2['score'];
}

usort($score_array);

['score']替换为从字符串中提取分数

答案 1 :(得分:2)

$array = array(
    0 => "title|url|12|user|date",
    1 => "title|url|0|user|date",
    2 => "title|url|13|user|date",
    3 => "title|url|0|user|date"
);

function sortOnScore( $a, $b )
{
    // discard first two values
    list( ,,$scoreA ) = explode( '|', $a );
    list( ,,$scoreB ) = explode( '|', $b );

    return $scoreA == $scoreB ? 0 : ( $scoreA > $scoreB ? 1 : -1 );
}

usort( $array, 'sortOnScore' );

var_dump( $array );

答案 2 :(得分:1)

首先,您需要将字符串转换为explode的数组,以便进行比较:

// If using PHP >= 5.3, this can also be made into an anonymous function
function converter($string) {
    $result = array_combine(
        array('title', 'url', 'score', 'user', 'date'),
        explode('|', $string)
    );

    // When these are later compared, it should be as numbers
    $result['score'] = (int)$result['score'];
    return $result;
}

$input = array(
    'Foo|http://foo|0|user1|today',
    // etc.
);
$converted = array_map('converter', $input);

这会使$converted看起来像:

array (
  0 => array (
    'title' => 'Foo',
    'url' => 'http://foo',
    'score' => '0',
    'user' => 'user1',
    'date' => 'today',
  ),
)

然后,您可以使用我的回答here中的代码对数组进行排序,方法是轻松指定所需的任何排序条件:

usort($converted, make_converter('score', 'date', 'title'));

答案 3 :(得分:1)

就个人而言,我很想迭代数组,将它拆分为|并将其放入一个新的多维数组中,例如:

[0] => array([title]=>'title',[url]=>'url',[score]=>'score',[user]=>'user',[date]=>'date')
[1] => array([title]=>'title',[url]=>'url',[score]=>'score',[user]=>'user',[date]=>'date')

然后它变得很容易排序,只需使用这样的函数:

function sortmulti ($array, $index, $order, $natsort=FALSE, $case_sensitive=FALSE) {
         if(is_array($array) && count($array)>0) {
             foreach(array_keys($array) as $key) { 
                $temp[$key]=$array[$key][$index];
             }
             if(!$natsort) {
                 if ($order=='asc') {
                     asort($temp);
                 } else {    
                     arsort($temp);
                 }
             }
             else 
             {
                 if ($case_sensitive===true) {
                     natsort($temp);
                 } else {
                     natcasesort($temp);
                 }
                if($order!='asc') { 
                 $temp=array_reverse($temp,TRUE);
                }
             }
             foreach(array_keys($temp) as $key) { 
                 if (is_numeric($key)) {
                     $sorted[]=$array[$key];
                 } else {    
                     $sorted[$key]=$array[$key];
                 }
             }
             return $sorted;
         }
     return $sorted;
 }

即。这样做:

$sortedarray = sortmulti($array,'score','asc');

答案 4 :(得分:1)

使用asort函数非常容易:

$pattern = '#^([^|]+)\|([^|]+)\|([^|]+)\|([^|]+)\|([^|]+)$#';
$sorted = array();
foreach($data as $s) $sorted[] = preg_replace($pattern, '$3|$1|$2|$4|$5', $s);
asort($sorted);


这4行代码,给出$ data:

Array
(
    [0] => title_0|url_0|6|user_0|date_0
    [1] => title_1|url_1|6|user_1|date_1
    [2] => title_2|url_2|2|user_2|date_2
    [3] => title_3|url_3|3|user_3|date_3
    [4] => title_4|url_4|2|user_4|date_4
    [5] => title_5|url_5|7|user_5|date_5
    [6] => title_6|url_6|3|user_6|date_6
    [7] => title_7|url_7|8|user_7|date_7
    [8] => title_8|url_8|3|user_8|date_8
    [9] => title_9|url_9|9|user_9|date_9
)

将生成$ sorted:

Array
(
    [2] => 2|title_2|url_2|user_2|date_2
    [4] => 2|title_4|url_4|user_4|date_4
    [3] => 3|title_3|url_3|user_3|date_3
    [6] => 3|title_6|url_6|user_6|date_6
    [8] => 3|title_8|url_8|user_8|date_8
    [0] => 6|title_0|url_0|user_0|date_0
    [1] => 6|title_1|url_1|user_1|date_1
    [5] => 7|title_5|url_5|user_5|date_5
    [7] => 8|title_7|url_7|user_7|date_7
    [9] => 9|title_9|url_9|user_9|date_9
)

再加上2行,您可以按原始顺序/格式将数组的每个元素中的项目放回原来:

$data = array();
foreach($sorted as $s) $data[] = preg_replace($pattern, '$2|$3|$1|$4|$5', $s);

将$ data设置为:

Array
(
    [0] => title_2|url_2|2|user_2|date_2
    [1] => title_4|url_4|2|user_4|date_4
    [2] => title_3|url_3|3|user_3|date_3
    [3] => title_6|url_6|3|user_6|date_6
    [4] => title_8|url_8|3|user_8|date_8
    [5] => title_0|url_0|6|user_0|date_0
    [6] => title_1|url_1|6|user_1|date_1
    [7] => title_5|url_5|7|user_5|date_5
    [8] => title_7|url_7|8|user_7|date_7
    [9] => title_9|url_9|9|user_9|date_9
)

答案 5 :(得分:0)

创建一个新的数组数组:

[0] => array("score", old_array[0])

然后排序。