Как отсортировать многомерный массив в PHP

У меня есть данные CSV, загруженные в многомерный массив. Таким образом, каждая «строка» является записью, а каждый «столбец» содержит данные одного и того же типа. Я использую функцию ниже, чтобы загрузить файл CSV.

function f_parse_csv($file, $longest, $delimiter)
{
  $mdarray = array();
  $file    = fopen($file, "r");
  while ($line = fgetcsv($file, $longest, $delimiter))
  {
    array_push($mdarray, $line);
  }
  fclose($file);
  return $mdarray;
}

Мне нужно указать столбец для сортировки, чтобы он переставлял строки. Один из столбцов содержит информацию о дате в формате Y-m-d H:i:s, и я хотел бы иметь возможность сортировать с самой последней датой, являющейся первой строкой.


person Melikoth    schedule 18.09.2008    source источник
comment
(2 года спустя...) Если вы сортируете даты, хранящиеся в виде строк, вам может понадобиться сначала использовать strtotime [1] docs.php.net/manual/en/function.strtotime.php   -  person Dan Burton    schedule 19.05.2010
comment
@deceze, stackoverflow.com/q/1597736/1709587 кажется мне лучшей целью для обмана. Это более точный дубликат, и ответы там доходят до сути быстрее, чем ваши на stackoverflow.com/a/17364128/1709587 при одинаковом уровне детализации. Что вы скажете о переключении цели? (Раскрытие информации: возможно, я предвзят как автор одного из ответов на цель обмана, которую я предлагаю.)   -  person Mark Amery    schedule 29.06.2019
comment
См. также: stackoverflow.com/questions/1597736/   -  person dreftymac    schedule 30.07.2019


Ответы (11)


Вы можете использовать array_multisort()

Попробуйте что-то вроде этого:

foreach ($mdarray as $key => $row) {
    // replace 0 with the field's index/key
    $dates[$key]  = $row[0];
}

array_multisort($dates, SORT_DESC, $mdarray);

Для PHP >= 5.5.0 просто извлеките столбец для сортировки. Нет необходимости в цикле:

array_multisort(array_column($mdarray, 0), SORT_DESC, $mdarray);
person Shinhan    schedule 18.09.2008
comment
Так что в этом примере $mdarray может быть двумерным массивом, таким как массив записей базы данных. В этом примере 0 — это индекс столбца «дата» в каждой записи (или строке). Таким образом, вы создаете массив $dates (в основном тот же массив, но только с этим столбцом) и указываете функции array_multisort сортировать $mdarray на основе значений этого конкретного столбца. - person Dan Burton; 19.05.2010
comment
Для ясности вы можете добавить в начало этого примера $dates = array(); - person Dan Burton; 19.05.2010
comment
Должен ли array_multisort работать с ассоциативными массивами (изменение $row[0] на $row['whatever']? Не идите сюда. После того, как я изменил свой массив на числовой, функция заработала, как и ожидалось. - person a coder; 15.02.2013
comment
Разве включение $key не является ненужным при использовании array_multisort()? Кажется, проще и преднамереннее написать foreach ($mdarray as $row) { $sortByDate[] = $row['date']; }, а затем array_multisort( $sortByDate, SORT_DESC, $mdarray ); (ваш семантический пробег может варьироваться). - person Mark Fox; 14.03.2013
comment
Если ответом является array_multi_sort(), вопрос не был понят. Хотя технически это будет работать, обычно есть лучшее решение с функцией сравнения, созданной пользователем, и использованием функции usort(). Его легче поддерживать. При мультисортировке вы обычно создаете код, который подготавливает данные к сортировке. Если структура данных изменится, этот код может быть выброшен. С помощью usort() вы изменяете функцию сравнения точно так же, как вы меняли структуру данных. - person Sven; 17.07.2013
comment
Теперь на странице PHP array_multisort есть более обширный пример этого ответа: php.net/manual/en/function.array-multisort.php#example-4928. - person icc97; 27.09.2013
comment
Предупреждение: array_multisort(): размеры массивов несовместимы - person RaviPatidar; 24.10.2016

Представляем: очень обобщенное решение для PHP 5.3+

Я хотел бы добавить сюда свое собственное решение, поскольку оно предлагает функции, которых нет в других ответах.

В частности, преимущества этого решения включают в себя:

  1. Его можно повторно использовать: вы указываете столбец сортировки как переменную, а не жестко кодируете его.
  2. Он гибкий: вы можете указать несколько столбцов сортировки (столько, сколько хотите) — дополнительные столбцы используются в качестве разрешения конфликтов между элементами, которые изначально сравниваются равными.
  3. Он обратим: вы можете указать, что сортировка должна быть обратной — индивидуально для каждого столбца.
  4. Он расширяемый: если набор данных содержит столбцы, которые нельзя сравнивать "тупым" способом (например, строки даты), вы также можете указать, как преобразовать эти элементы в значение, которое можно сравнивать напрямую (например, экземпляр DateTime).
  5. Он ассоциативен, если хотите: этот код заботится о сортировке элементов, но вы выбираете фактическую функцию сортировки (usort или uasort).
  6. Наконец, он не использует array_multisort: хотя array_multisort удобен, он зависит от создания проекции всех ваших входных данных перед сортировкой. Это требует времени и памяти и может быть просто недопустимым, если ваш набор данных велик.

Код

function make_comparer() {
    // Normalize criteria up front so that the comparer finds everything tidy
    $criteria = func_get_args();
    foreach ($criteria as $index => $criterion) {
        $criteria[$index] = is_array($criterion)
            ? array_pad($criterion, 3, null)
            : array($criterion, SORT_ASC, null);
    }

    return function($first, $second) use (&$criteria) {
        foreach ($criteria as $criterion) {
            // How will we compare this round?
            list($column, $sortOrder, $projection) = $criterion;
            $sortOrder = $sortOrder === SORT_DESC ? -1 : 1;

            // If a projection was defined project the values now
            if ($projection) {
                $lhs = call_user_func($projection, $first[$column]);
                $rhs = call_user_func($projection, $second[$column]);
            }
            else {
                $lhs = $first[$column];
                $rhs = $second[$column];
            }

            // Do the actual comparison; do not return if equal
            if ($lhs < $rhs) {
                return -1 * $sortOrder;
            }
            else if ($lhs > $rhs) {
                return 1 * $sortOrder;
            }
        }

        return 0; // tiebreakers exhausted, so $first == $second
    };
}

Как использовать

В этом разделе я буду предоставлять ссылки, которые сортируют этот примерный набор данных:

$data = array(
    array('zz', 'name' => 'Jack', 'number' => 22, 'birthday' => '12/03/1980'),
    array('xx', 'name' => 'Adam', 'number' => 16, 'birthday' => '01/12/1979'),
    array('aa', 'name' => 'Paul', 'number' => 16, 'birthday' => '03/11/1987'),
    array('cc', 'name' => 'Helen', 'number' => 44, 'birthday' => '24/06/1967'),
);

Основы

Функция make_comparer принимает переменное количество аргументов, определяющих желаемую сортировку, и возвращает функцию, которую вы должны использовать в качестве аргумента для usort или uasort.

Самый простой вариант использования — передать ключ, который вы хотели бы использовать для сравнения элементов данных. Например, чтобы отсортировать $data по элементу name, вы должны сделать

usort($data, make_comparer('name'));

Посмотрите в действии.

Ключ также может быть числом, если элементы представляют собой массивы с числовым индексом. Для примера в вопросе это будет

usort($data, make_comparer(0)); // 0 = first numerically indexed column

Посмотрите в действии.

Несколько столбцов сортировки

Вы можете указать несколько столбцов сортировки, передав дополнительные параметры в make_comparer. Например, для сортировки по «числу», а затем по столбцу с нулевым индексом:

usort($data, make_comparer('number', 0));

Посмотрите в действии.

Расширенные возможности

Более продвинутые функции доступны, если вы укажете столбец сортировки как массив, а не как простую строку. Этот массив должен быть численно проиндексирован и должен содержать следующие элементы:

0 => the column name to sort on (mandatory)
1 => either SORT_ASC or SORT_DESC (optional)
2 => a projection function (optional)

Давайте посмотрим, как мы можем использовать эти функции.

Обратная сортировка

Чтобы отсортировать имя по убыванию:

usort($data, make_comparer(['name', SORT_DESC]));

Посмотрите в действии.

Чтобы отсортировать по убыванию номера, а затем по убыванию имени:

usort($data, make_comparer(['number', SORT_DESC], ['name', SORT_DESC]));

Посмотрите в действии.

Пользовательские проекции

В некоторых сценариях может потребоваться сортировка по столбцу, значения которого плохо поддаются сортировке. Столбец «день рождения» в выборке данных соответствует этому описанию: нет смысла сравнивать дни рождения как строки (поскольку, например, «01.01.1980» предшествует «10.10.1970»). В этом случае мы хотим указать, как проецировать фактические данные в форму, которую можно напрямую сравнивать с желаемой семантикой.

Проекции могут быть указаны как любой тип вызываемых: как строки, массивы или анонимные функции. Предполагается, что проекция принимает один аргумент и возвращает его спроецированную форму.

Следует отметить, что, хотя проекции похожи на пользовательские функции сравнения, используемые с usort и семейством, они проще (вам нужно только преобразовать одно значение в другое) и использовать все функции, уже встроенные в make_comparer.

Давайте отсортируем примерный набор данных без проекции и посмотрим, что получится:

usort($data, make_comparer('birthday'));

Посмотрите в действии.

Это не было желаемым результатом. Но мы можем использовать date_create в качестве проекции:

usort($data, make_comparer(['birthday', SORT_ASC, 'date_create']));

Посмотрите в действии.

Это правильный порядок, который мы хотели.

Есть много других вещей, которых можно достичь с помощью проекций. Например, быстрый способ получить сортировку без учета регистра — использовать strtolower в качестве проекции.

Тем не менее, я должен также упомянуть, что лучше не использовать проекции, если ваш набор данных большой: в этом случае было бы намного быстрее спроецировать все ваши данные вручную заранее, а затем отсортировать без использования проекции, хотя это приведет к обмену увеличенное использование памяти для более высокой скорости сортировки.

Наконец, вот пример, который использует все возможности: сначала сортирует по убыванию числа, затем по возрастанию дня рождения:

usort($data, make_comparer(
    ['number', SORT_DESC],
    ['birthday', SORT_ASC, 'date_create']
));

Посмотрите в действии.

person Jon    schedule 28.05.2013
comment
@Jon Когда я проверяю ваше последнее действие (с обратным вызовом date_create), дни рождения идут в неправильном порядке. Не могли бы вы подтвердить ? Я получаю 01/12/1979, 03/11/1987, 12/03/1980 и 24/06/1967. Если вместо этого я использую strtotime, я получаю хороший результат. Я предполагаю, что это DateTime, который сломан. - person David Bélanger; 08.08.2013
comment
@DavidBélanger: Какой именно URL? Все примеры корректно работают как на ideone.com, так и на моей локальной машине. - person Jon; 09.08.2013
comment
Привет, @Jon, я не знаю, как я могу связаться с тобой, кроме как через комментарий. Я вижу, вы создали многомерный массив тегов, но нам нужны также многомерные данные для аналогичного термина в визуализации данных и смежных дисциплинах. Я не могу создавать теги, могу я попросить вас создать их, если вы сочтете это целесообразным? - person VividD; 09.01.2014
comment
@VividD: я не создавал тег сам, и создание тега не может произойти само по себе. Новые теги неявно создаются, когда кто-то с необходимыми привилегиями использует их для пометки вопроса; учитывая, что я никогда не видел и, вероятно, никогда не увижу вопрос, который, по моему мнению, должен быть помечен таким образом, я не могу помочь. - person Jon; 09.01.2014
comment
Не могли бы вы привести пример, как реализовать сортировку без учета регистра? Я пытался преобразовать проекцию в нижний регистр, но это не сработает... - person Andrew; 18.03.2014
comment
@Andrew: пример. Но помните, что это неэффективно, поэтому не делайте этого, если ваш набор данных не мал. - person Jon; 18.03.2014
comment
@Jon, спасибо, я только что попробовал, и он на 0,006 секунды медленнее, чем без него, сортируя 200 строк. Думаю, я приму такую ​​неэффективность :) - person Andrew; 18.03.2014
comment
У меня есть другой массив значений, по которым я хотел бы отсортировать столбец, и значение в столбце может иметь несколько совпадений. Массив сортировки состоит из типов файлов, поэтому я всегда хочу, чтобы типы файлов списка файлов отображались в определенном порядке. Возможно ли это в этой конструкции? - person Ecropolis; 27.05.2014
comment
@Ecropolis: Пожалуйста, разместите хороший пример ваших входных данных и желаемого результата где-нибудь (например, ideone.com или pastebin.com), чтобы мы могли устранить недоразумения. - person Jon; 27.05.2014
comment
@Jon - Спасибо, вот примеры массивов с комментариями. ideone.com/utbrNt - person Ecropolis; 28.05.2014
comment
@Ecropolis: Хорошо, так что вы можете создать массив, где ключи — это типы файлов, а значения — веса (меньший вес = элемент идет сверху) с помощью $weights = array_flip($sort_array). $weights теперь ['mp4' => 0, 'mpeg' => 1, ...]. Затем вы можете использовать это в компараторе, отсортировав по типу файла и используя это как проекцию: function($t) use ($weights) { return $weights[$t]; }). - person Jon; 28.05.2014
comment
Превосходно! Спасибо @Джон. Я обновил ideone.com/utbrNt для полного примера того, как использовать эту функцию для сортировки массива, используя другую для ссылочные значения сортировки. - person Ecropolis; 29.05.2014
comment
@Ecropolis: у вас есть лишние кавычки вокруг function($t) ..., которые нужно удалить. Ваше здоровье! - person Jon; 29.05.2014
comment
@Jon - Спасибо за всю вашу помощь. Я попытался реализовать это на своем сервере, и я получаю это: Ошибка синтаксического анализа PHP: синтаксическая ошибка, неожиданная '[', ожидание ')' - я пробовал разные варианты, я просто немного не понимаю, как это на самом деле работает. У меня v5.3.28 - ideone.com работает на php 5.4 - в этом проблема? - person Ecropolis; 06.06.2014
comment
@Ecropolis: PHP 5.3 не поддерживает короткий синтаксис массива [...], вместо этого вам придется использовать array(...). Я не делал этого в примерах для большей краткости, но сам make_comparer совместим с 5.3. - person Jon; 06.06.2014
comment
@Jon Отличный ответ, и я согласен, что это больше похоже на веб-сайт, чем на ответ. Спасибо. Только есть один вопрос. Как я могу заставить его работать для объектов? - person YahyaE; 04.10.2014
comment
@YahyaE: Сортировка массивов объектов? Замените $first[$column] на $first->$column и то же самое на $second. Всего четыре замены. - person Jon; 10.10.2014
comment
мой массив 4D? как я могу передать индекс, если это возможно? - person Dashrath; 16.11.2014
comment
@Dashrath: я не уверен, что у тебя за структура. Либо передайте $array['index'], если хотите избавиться от верхнего уровня, либо используйте проекцию function($sub) { return $sub['index']; }, если хотите избавиться от измерения среднего уровня с именем index. - person Jon; 18.11.2014
comment
@CalculatingMachine Я прочитал вопрос, но вы не показываете, что пытались сделать. Кажется, usort($data['content'], get_comparer('price')) будет достаточно, но я не уверен. - person Jon; 22.04.2016
comment
@Jon спасибо за ваш комментарий. Тем не менее, я все еще читаю ваш ответ и пытаюсь его понять. При необходимости я буду использовать то же самое в своем проекте. Просто было одно сомнение. Я не уверен, что это будет работать с моими данными/массивом или нет. В вашем примере данные в другом формате. - person Rocx; 22.04.2016

С помощью usort. Вот общее решение, которое вы можете использовать для разных столбцов:

class TableSorter {
  protected $column;
  function __construct($column) {
    $this->column = $column;
  }
  function sort($table) {
    usort($table, array($this, 'compare'));
    return $table;
  }
  function compare($a, $b) {
    if ($a[$this->column] == $b[$this->column]) {
      return 0;
    }
    return ($a[$this->column] < $b[$this->column]) ? -1 : 1;
  }
}

Для сортировки по первому столбцу:

$sorter = new TableSorter(0); // sort by first column
$mdarray = $sorter->sort($mdarray);
person troelskn    schedule 18.09.2008
comment
Я получаю сообщение об ошибке синтаксического анализа: ошибка синтаксического анализа, непредвиденная T_STRING, ожидание T_OLD_FUNCTION, T_FUNCTION, T_VAR или '}' во второй строке этого класса. - person Melikoth; 19.09.2008
comment
Замените защищенный на var и __construct на TableSorter, и он будет работать в PHP4. Однако обратите внимание, что поддержка PHP4 прекращена. - person troelskn; 19.09.2008
comment
Я установил PHP на v5, не знал, что по умолчанию работает v4. Посмотрев на него некоторое время, я думаю, что понимаю, как изменить его для разных типов сортов. - person Melikoth; 19.09.2008

Сортировка нескольких строк с использованием замыкания

Вот еще один подход, использующий uasort() и анонимную функцию обратного вызова (замыкание). Я использовал эту функцию регулярно. Требуется PHP 5.3 — больше никаких зависимостей!

/**
 * Sorting array of associative arrays - multiple row sorting using a closure.
 * See also: http://the-art-of-web.com/php/sortarray/
 *
 * @param array $data input-array
 * @param string|array $fields array-keys
 * @license Public Domain
 * @return array
 */
function sortArray( $data, $field ) {
    $field = (array) $field;
    uasort( $data, function($a, $b) use($field) {
        $retval = 0;
        foreach( $field as $fieldname ) {
            if( $retval == 0 ) $retval = strnatcmp( $a[$fieldname], $b[$fieldname] );
        }
        return $retval;
    } );
    return $data;
}

/* example */
$data = array(
    array( "firstname" => "Mary", "lastname" => "Johnson", "age" => 25 ),
    array( "firstname" => "Amanda", "lastname" => "Miller", "age" => 18 ),
    array( "firstname" => "James", "lastname" => "Brown", "age" => 31 ),
    array( "firstname" => "Patricia", "lastname" => "Williams", "age" => 7 ),
    array( "firstname" => "Michael", "lastname" => "Davis", "age" => 43 ),
    array( "firstname" => "Sarah", "lastname" => "Miller", "age" => 24 ),
    array( "firstname" => "Patrick", "lastname" => "Miller", "age" => 27 )
);

$data = sortArray( $data, 'age' );
$data = sortArray( $data, array( 'lastname', 'firstname' ) );
person feeela    schedule 13.04.2012

Я знаю, что прошло 2 года с тех пор, как этот вопрос был задан и на него был дан ответ, но вот еще одна функция, которая сортирует двумерный массив. Он принимает переменное количество аргументов, что позволяет вам передавать более одного ключа (например, имя столбца) для сортировки. Требуется PHP 5.3.

function sort_multi_array ($array, $key)
{
  $keys = array();
  for ($i=1;$i<func_num_args();$i++) {
    $keys[$i-1] = func_get_arg($i);
  }

  // create a custom search function to pass to usort
  $func = function ($a, $b) use ($keys) {
    for ($i=0;$i<count($keys);$i++) {
      if ($a[$keys[$i]] != $b[$keys[$i]]) {
        return ($a[$keys[$i]] < $b[$keys[$i]]) ? -1 : 1;
      }
    }
    return 0;
  };

  usort($array, $func);

  return $array;
}

Попробуйте здесь: http://www.exorithm.com/algorithm/view/sort_multi_array

person Mike C    schedule 19.11.2010
comment
Можно ли заменить первые 3 строки функции на $keys = func_get_args(); array_unshift($keys);? - person ; 13.03.2012

Вы можете отсортировать массив с помощью функции usort.

 $array = array(
  array('price'=>'1000.50','product'=>'product 1'),
  array('price'=>'8800.50','product'=>'product 2'),
  array('price'=>'200.0','product'=>'product 3')
);

function cmp($a, $b) {
  return $a['price'] > $b['price'];
}
usort($array, "cmp");
print_r($array);

Выход :

Array
(
    [0] => Array
        (
            [price] => 134.50
            [product] => product 1
        )

    [1] => Array
        (
            [price] => 2033.0
            [product] => product 3
        )

    [2] => Array
        (
            [price] => 8340.50
            [product] => product 2
        )

)

Пример

person Kamal    schedule 30.06.2014

Вот класс php4/php5, который будет сортировать одно или несколько полей:

// a sorter class
//  php4 and php5 compatible
class Sorter {

  var $sort_fields;
  var $backwards = false;
  var $numeric = false;

  function sort() {
    $args = func_get_args();
    $array = $args[0];
    if (!$array) return array();
    $this->sort_fields = array_slice($args, 1);
    if (!$this->sort_fields) return $array();

    if ($this->numeric) {
      usort($array, array($this, 'numericCompare'));
    } else {
      usort($array, array($this, 'stringCompare'));
    }
    return $array;
  }

  function numericCompare($a, $b) {
    foreach($this->sort_fields as $sort_field) {
      if ($a[$sort_field] == $b[$sort_field]) {
        continue;
      }
      return ($a[$sort_field] < $b[$sort_field]) ? ($this->backwards ? 1 : -1) : ($this->backwards ? -1 : 1);
    }
    return 0;
  }

  function stringCompare($a, $b) {
    foreach($this->sort_fields as $sort_field) {
      $cmp_result = strcasecmp($a[$sort_field], $b[$sort_field]);
      if ($cmp_result == 0) continue;

      return ($this->backwards ? -$cmp_result : $cmp_result);
    }
    return 0;
  }
}

/////////////////////
// usage examples

// some starting data
$start_data = array(
  array('first_name' => 'John', 'last_name' => 'Smith', 'age' => 10),
  array('first_name' => 'Joe', 'last_name' => 'Smith', 'age' => 11),
  array('first_name' => 'Jake', 'last_name' => 'Xample', 'age' => 9),
);

// sort by last_name, then first_name
$sorter = new Sorter();
print_r($sorter->sort($start_data, 'last_name', 'first_name'));

// sort by first_name, then last_name
$sorter = new Sorter();
print_r($sorter->sort($start_data, 'first_name', 'last_name'));

// sort by last_name, then first_name (backwards)
$sorter = new Sorter();
$sorter->backwards = true;
print_r($sorter->sort($start_data, 'last_name', 'first_name'));

// sort numerically by age
$sorter = new Sorter();
$sorter->numeric = true;
print_r($sorter->sort($start_data, 'age'));
person Devon    schedule 18.09.2008
comment
Это работает только с ассоциативными массивами? - person Melikoth; 19.09.2008
comment
да - только ассоциативные массивы. Теперь, когда я смотрю на это, это не правильное решение этой проблемы. - person Devon; 23.09.2008

Вам поможет функция Usort.
http://php.net/usort

person Jan Hančič    schedule 18.09.2008
comment
Я проголосовал за вас из-за того, что вы не смогли предоставить решение с объяснением и примерами исходного вопроса. Обновите свой ответ, и я отменю свой голос. - person crafter; 05.04.2017

Прежде чем я смог запустить класс TableSorter, я придумал функцию, основанную на том, что предоставил Shinhan.

function sort2d_bycolumn($array, $column, $method, $has_header)
  {
  if ($has_header)  $header = array_shift($array);
  foreach ($array as $key => $row) {
    $narray[$key]  = $row[$column]; 
    }
  array_multisort($narray, $method, $array);
  if ($has_header) array_unshift($array, $header);
  return $array;
  }
  • $array — это массив MD, который вы хотите отсортировать.
  • $column — это столбец, по которому вы хотите выполнить сортировку.
  • $method — это то, как вы хотите выполнить сортировку, например SORT_DESC.
  • $has_header имеет значение true, если первая строка содержит значения заголовков, которые вы не хотите сортировать.
person Melikoth    schedule 18.09.2008

Я пробовал несколько популярных ответов array_multisort() и usort(), и ни один из них не работал у меня. Данные просто смешиваются, а код становится нечитаемым. Вот быстрое грязное решение. ВНИМАНИЕ: используйте это только в том случае, если вы уверены, что мошеннический разделитель не вернется, чтобы преследовать вас позже!

Допустим, каждая строка в вашем множественном массиве выглядит так: имя, материал1, материал2:

// Sort by name, pull the other stuff along for the ride
foreach ($names_stuff as $name_stuff) {
    // To sort by stuff1, that would be first in the contatenation
    $sorted_names[] = $name_stuff[0] .','. name_stuff[1] .','. $name_stuff[2];
}
sort($sorted_names, SORT_STRING);

Нужно вернуть вещи в алфавитном порядке?

foreach ($sorted_names as $sorted_name) {
    $name_stuff = explode(',',$sorted_name);
    // use your $name_stuff[0] 
    // use your $name_stuff[1] 
    // ... 
}

Да, грязно. Но очень легко, не взорвет вашу голову.

person PJ Brunet    schedule 19.06.2013

Я предпочитаю использовать array_multisort. См. документацию здесь.

person Tim Boland    schedule 18.09.2008