Код
#статьи

Как отсортировать массив в PHP 13 способами: инструкция с примерами

Становимся настоящими ниндзя в сортировке массивов. Вместо оружия — встроенные функции PHP, быстрые и точные, как катана.

Иллюстрация: Polina Vari для Skillbox Media

В PHP массивом называют структуру данных, которая позволяет хранить упорядоченный набор значений по принципу ключ => значение. И количество инструментов для работы с массивами тут впечатляет: для одной только сортировки существует 13 встроенных функций! В этой статье мы покажем, как ими пользоваться, чтобы получать информацию в нужном виде.

Способы сортировки

Все функции PHP для сортировки массивов «конструируются» из четырёх основных критериев:

  • вид сортировки — по ключу или значениям;
  • порядок сортировки — восходящий, нисходящий, естественный, пользовательский и прочие;
  • способ обработки ключей — с сохранением связи или нет;
  • наличие уточняющих опций — в семи из этих функций можно указать предпочтительный способ сортировки и дополнительные параметры («флаги»).

Вот функции, которые позволяют это сделать:

Список функций сортировки массивов в PHP
Изображение: Евгений Колесников для Skillbox Media

У каждой из функций есть название, указывающее на вид сортировки и завершающееся круглыми скобками. Эти названия на первый взгляд кажутся не особо говорящими, поэтому для начала лучше выбирать функцию под конкретную задачу, сверяясь с табличкой на официальном сайте. При этом легко запомнить, что функции с буквой «k» сортируют массивы по ключам.

В зависимости от выбранной функции внутри скобок указывается массив или несколько массивов для сортировки, а затем могут идти опции (флаги):

  • SORT_REGULAR — сравнивать элементы в нормальном порядке, не меняя типов;
  • SORT_NUMERIC — сравнивать элементы как числа;
  • SORT_STRING — сравнивать элементы как строки;
  • SORT_LOCALE_STRING — сравнивать элементы как строки, руководствуясь текущим местонахождением, то есть локалью (Locale);
  • SORT_NATURAL — сравнивать элементы как строки в естественном порядке;
  • SORT_FLAG_CASE — можно объединить с SORT_STRING или SORT_NATURAL, чтобы сделать сортировку нечувствительной к регистру.

Давайте попробуем в действии отсортировать массивы разными способами. В этом нам помогут редактор кода Notepad++ и среда разработки XAMPP для запуска PHP-кода в браузере.

Во всех примерах будем сначала выводить исходный массив, а затем его же после сортировки (помните, что сортировка меняет массив, то есть её результат сохраняется). Для удобства чтения будем осуществлять вывод с помощью привычной функции echo в связке с implode()/print_r() или циклом foreach.

Также для красоты будем сопровождать результаты подписями (HTML-заголовки <h2> и <h3>) и переносом строк (HTML-элемент <br>).

<?php
    echo "<h1>СОРТИРОВКА МАССИВОВ</h1>";
Начало нашего кода

Числовая сортировка: зарплаты

Создадим массив чисел и отсортируем его в порядке убывания, от большего значения к меньшему. Возьмём самый простой пример: массив зарплат в рублях:

$salaries = array(45000, 65000, 35000, 75000, 55000);

Так он выглядит с выводом результата.

 echo "<h2>Сортировка вакансий по зарплатам</h2>";
   $salaries = array(45000, 65000, 35000, 75000, 55000);
   		 
echo "<h3>Исходный массив вакансий по зарплатам целиком, до сортировки</h3>";
   print_r($salaries);
   	 
 echo "<h3>Массив вакансий по зарплатам до сортировки –- только значения (исходный порядок)</h3>";
   echo implode(", ", $salaries) . "<br>";

Код исходного массива зарплат с выводом результата

Исходный массив вакансий по зарплатам целиком, до сортировки:

Array ( [0] => 45000 [1] => 65000 [2] => 35000 [3] => 75000 [4] => 55000 )

Массив вакансий по зарплатам до сортировки — только значения (исходный порядок):

45000, 65000, 35000, 75000, 55000

Как видим, сейчас зарплаты внутри массива расположены в произвольном порядке, а нам бы хотелось сначала увидеть самые выгодные вакансии. Значит, надо найти в таблице такой метод, который умеет сортировать значения в порядке убывания — нам подойдёт rsort().

rsort($array, FLAGS);

Объяснение:

  • rsort() — название функции, в скобках указываются параметры;
  • $array — массив для сортировки;
  • на месте опции FLAGS можно указать другие правила сортировки массива (флаги).

А теперь попробуем нашу функцию в деле. На первом шаге передадим в неё массив с зарплатами — $salaries.

rsort($salaries);

Далее прописываем вывод результата:

echo "<h3>Массив вакансий по зарплатам после сортировки через rsort() (по значению, по убыванию)</h3>";
echo implode(", ", $salaries) . "<br>";
Код для сортировки массива зарплат

Вот что у нас получилось на выходе:

75000, 65000, 55000, 45000, 35000

Теперь возьмёмся за массив текстовых значений.

Текстовая сортировка: виды птиц

По данным Большой российской энциклопедии, в мире насчитывается более двухсот видов сов. Было бы неплохо создать про них сайт, чтобы каждый мог узнать о совах побольше! Начнём с создания «массива сов», руководствуясь книгой Ю. Б. Пукинского «Жизнь сов».

    	echo "<h2>Сортируем сов</h2>";
   		 $owls = array(
   			 "tytonidae" => "Сипухи",
   			 "tyto" => "Сипухи",
   			 "strigidae" => "Настоящие совы",
   			 "otus" => "Совки",
   			 "bubo" => "Филины",
   			 "ketupa" => "Рыбные совы",
   			 "nyctea" => "Белые совы",
   			 "surnia" => "Ястребиные совы",
   			 "glaucidium" => "Сычики",
   			 "ninox" => "Иглоногие совы",
   			 "athene" => "Сычи",
   			 "strix" => "Неясыти",
   			 "asfo" => "Ушастые совы",
   			 "aegolius" => "Мохноногие сычи"
   		 );

Код исходного массива видов сов
echo "<h3>Исходный массив названий видов сов целиком, до сортировки</h3>";
   print_r($owls);
   		 
echo "<h3>Названия видов сов до сортировки -- только значения (исходный порядок)</h3>";
   echo implode(", ", $owls) . "<br>";

Код вывода исходного массива видов сов

Исходный массив названий видов сов целиком, до сортировки:

Array ( [tytonidae] => Сипухи [tyto] => Сипухи [strigidae] => Настоящие совы [otus] => Совки [bubo] => Филины [ketupa] => Рыбные совы [nyctea] => Белые совы [surnia] => Ястребиные совы [glaucidium] => Сычики [ninox] => Иглоногие совы [athene] => Сычи [strix] => Неясыти [asfo] => Ушастые совы [aegolius] => Мохноногие сычи )

Названия видов сов до сортировки — только значения (исходный порядок):

Сипухи, Сипухи, Настоящие совы, Совки, Филины, Рыбные совы, Белые совы, Ястребиные совы, Сычики, Иглоногие совы, Сычи, Неясыти, Ушастые совы, Мохноногие сычи

В данном случае в роли ключей ассоциативного массива у нас выступают латинские названия видов, а значениями являются русские названия.

В зависимости от задачи нам может понадобиться как латинское, так и русское название. Кроме этого, было бы интересно иметь возможность получать информацию о случайно выбранной сове, а ещё — представлять текстовые значения в алфавитном порядке.

Отсюда вытекает необходимость использования сразу трёх различных функций сортировки:

  • ksort() для сортировки по ключам (латинским названиям) по алфавиту;
  • asort() для сортировки по значениям (русским названиям), также по алфавиту;
  • shuffle() для получения случайных русских названий сов.

Синтаксис ksort() и asort() такой же, как и в предыдущем примере у rsort(), а с shuffle() всё ещё проще — она принимает только название массива.

Посмотрим на функции в деле:

ksort($owls);
   echo"<h3>Названия видов сов после сортировки через ksort() (по ключу, по алфавиту, по возрастанию)</h3>";
   print_r(array_keys($owls));
   			 
asort($owls);
   echo "<h3>Названия видов сов после сортировки через asort() (по значению, по алфавиту, по возрастанию)</h3>";
   echo implode(", ", $owls) . "<br>";
   			 
shuffle($owls);
   echo "<h3>Названия видов сов после сортировки через shuffle() (по значению, случайный порядок)</h3>";
   echo implode(", ", $owls) . "<br>";
Код для сортировки массива видов сов

Названия видов сов после сортировки через ksort() (по ключу, по алфавиту, по возрастанию):

Array ( [0] => aegolius [1] => asfo [2] => athene [3] => bubo [4] => glaucidium [5] => ketupa [6] => ninox [7] => nyctea [8] => otus [9] => strigidae [10] => strix [11] => surnia [12] => tyto [13] => tytonidae )

Названия видов сов после сортировки через asort() (по значению, по алфавиту, по возрастанию):

Белые совы, Иглоногие совы, Мохноногие сычи, Настоящие совы, Неясыти, Рыбные совы, Сипухи, Сипухи, Совки, Сычи, Сычики, Ушастые совы, Филины, Ястребиные совы

Названия видов сов после сортировки через shuffle() (по значению, случайный порядок):

Сипухи, Рыбные совы, Белые совы, Сычики, Совки, Сипухи, Мохноногие сычи, Ястребиные совы, Ушастые совы, Филины, Неясыти, Настоящие совы, Иглоногие совы, Сычи

Совы встали на свои места, а мы двигаемся дальше — к сортировке, имитирующей человеческую логику.

Естественная сортировка: страницы во «ВКонтакте»

Предположим, у нас есть список подписчиков нашей группы в одном из возможных форматов — ссылками с id вида vk.com/idXXX.

echo "<h2>Сортируем ссылки на страницы во «Вконтакте» через natsort()</h2>";
   $pages = array("vk.com/id30000", "vk.com/id10000", "vk.com/id20000");
   		 
   echo "<h3>Исходный массив ссылок на страницы во «Вконтакте», до сортировки</h3>";
   print_r($pages);
Код исходного массива страниц во «Вконтакте» с выводом результата

Исходный массив ссылок на страницы во «Вконтакте», до сортировки:

Array ( [0] => vk.com/id30000 [1] => vk.com/id10000 [2] => vk.com/id20000 ) 

Было бы удобно расположить записи в порядке возрастания id, но есть нюанс: элементы массива являются строковыми значениями. Вот что показывает проверка типов:

echo "<h3>Проверка типа данных в массиве ссылок на страницы во «Вконтакте»</h3>";
   foreach ($pages as $page) {
   	echo gettype($page) . "<br>";
   };

Вывод результата после проверки типа данных в массиве ссылок на страницы во «Вконтакте»:

string
string
string

Чтобы решить задачу, воспользуемся функцией естественной сортировки natsort().

natsort($array);

Объяснение:

  • natsort() — название функции, в скобках указывается единственный параметр;
  • $array — массив, который нужно отсортировать естественным способом (как это бы сделал человек).

Посмотрим на функцию в деле:

natsort($pages);
   echo "<h3>Массив ссылок на страницы во «Вконтакте» после естественной сортировки через natsort() (по значению, по возрастанию)</h3>";
   echo implode(", ", $pages) . "<br>";

Массив ссылок на страницы во «Вконтакте» после естественной сортировки через natsort() (по значению, по возрастанию):

vk.com/id10000, vk.com/id20000, vk.com/id30000

Теперь страницы отсортированы в удобном для работы формате.

Сортировка многомерного массива: цены на топливо

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

echo "<h2>Сортируем цены на бензин и дизельное топливо (в рублях) через array_multisort()</h2>";
   	 $petrol = array(
   		array("52,75", "61,95", "54,01", "47,60"),
   		array("АИ-95", "АИ-98", "ДТ", "АИ-92")
   	 );
   		 
   	 echo "<h3>Марки топлива и цены на него до сортировки(исходный порядок)</h3>";
   	 print_r(array_values($petrol));
Код исходного массива цен на топливо с выводом результата

Марки топлива и цены на него до сортировки (исходный порядок):

Array ( [0] => Array ( [0] => 52,75 [1] => 61,95 [2] => 54,01 [3] => 47,60 ) [1] => Array ( [0] => АИ-95 [1] => АИ-98 [2] => ДТ [3] => АИ-92 ) )

Сейчас здесь есть взаимное соответствие (например, АИ-92 стоит 47,60), но сами значения не отсортированы в каком-либо порядке. Попробуем с помощью функции сортировки array_multisort() вывести для пользователя список ценников, отсортированный по возрастанию, где сначала идёт самый дешёвый бензин.

Функция array_multisort() предназначена как раз для сортировки многомерных массивов. Вот её синтаксис:

array_multisort($array1, $array1_sort_order, $array1_sort_flags, $other);

Объяснение:

  • array_multisort() — название функции, в скобках указываются параметры;
  • $array1 — первый массив для сортировки;
  • на месте опции $array1_sort_order можно указать порядок сортировки первого массива (можно не указывать);
  • на месте опции $array1_sort_flags можно указать другие правила сортировки первого массива (флаги) в дополнение к предыдущей опции;
  • на месте $other можно вписать ещё один массив $array2 с опциями или без (и так далее).

Применим функцию в деле:

echo("<h3>Сортировка марок топлива и цен через array_multisort() (по возрастанию)</h3>");
   	array_multisort($petrol[0], $petrol[1]);
   	echo implode(" -- ", $petrol[1]) . "<br>";
   	echo implode(" -- ", $petrol[0]) . "<br>";

Вывод отсортированного массива марок топлива и цен через array_multisort() (по возрастанию):

АИ-92 -- АИ-95 -- ДТ -- АИ-98
47,60--52,75--54,01--61,95

Теперь марки топлива расположены по возрастанию цены, а мы возьмём ещё более интересный пример — сортировку по кастомным правилам.

Пользовательская сортировка: сотрудники компании

Предположим, у нашей компании есть корпоративный портал, где можно посмотреть информацию о коллегах. Пусть у нас в массиве будет шесть коллег. База содержит Ф. И. О., внутренний ID, должность и возраст, а карточка каждого сотрудника является отдельным массивом многомерного массива:

  	echo "<h2>Сортируем сотрудников компании</h2>";
   		 $employees = array(
   			 array(
   				 "ID" => 1,
   				 "ФИО" => "Вувузела Андрей Павлович",
   				 "Должность" => "Менеджер",
   				 "Возраст" => "29"
   			 ),
   			 array(
   				 "ID" => 2,
   				 "ФИО" => "Ахрюнов Алексей Степанович",
   				 "Должность" => "Бухгалтер",
   				 "Возраст" => "32"
   			 ),
   			 array(
   				 "ID" => 3,
   				 "ФИО" => "Охрюненко Борис Гориславович",
   				 "Должность" => "Курьер",
   				 "Возраст" => "22"
   			 ),
   			 array(
   				 "ID" => 4,
   				 "ФИО" => "Бокакин Арсений Брониславович",
   				 "Должность" => "Менеджер",
   				 "Возраст" => "31"
   			 ),
   			 array(
   				 "ID" => 5,
   				 "ФИО" => "Голохрюхин Евгений Владимирович",
   				 "Должность" => "Директор",
   				 "Возраст" => "40"
   			 ),
   			 array(
   				 "ID" => 6,
   				 "ФИО" => "Совакошка Мария Игоревна",
   				 "Должность" => "Старший инженер",
   				 "Возраст" => "26"
   			 )
   		 );

Код вывода исходного массива карточек сотрудников компании:

echo "<h3>Записи сотрудников компании до сортировки(исходный порядок)</h3>";
   	print_r(array_values($employees));

Вывод исходного массива карточек сотрудников компании до сортировки (исходный порядок):

Array ( [0] => Array ( [ID] => 1 [ФИО] => Вувузела Андрей Павлович [Должность] => Менеджер [Возраст] => 29 ) [1] => Array ( [ID] => 2 [ФИО] => Ахрюнов Алексей Степанович [Должность] => Бухгалтер [Возраст] => 32 ) [2] => Array ( [ID] => 3 [ФИО] => Охрюненко Борис Гориславович [Должность] => Курьер [Возраст] => 22 ) [3] => Array ( [ID] => 4 [ФИО] => Бокакин Арсений Брониславович [Должность] => Менеджер [Возраст] => 31 ) [4] => Array ( [ID] => 5 [ФИО] => Голохрюхин Евгений Владимирович [Должность] => Директор [Возраст] => 40 ) [5] => Array ( [ID] => 6 [ФИО] => Совакошка Мария Игоревна [Должность] => Старший инженер [Возраст] => 26 ) ) 

Дадим пользователю корпоративного портала возможность сортировки списка по фамилиям, возрасту и порядковому номеру. В этом нам поможет функция пользовательской сортировки usort().

usort($array, "function");

Объяснение:

  • usort() — название функции, в скобках указываются параметры.
  • $array — массив для сортировки.
  • «function» — название вашей функции сравнения с собственными правилами сортировки. Она объявляется заранее и принимает два параметра. Обратите внимание на кавычки, в которые заключается название.

Применим функцию в деле — на сортировке сотрудников по алфавиту, по возрасту (по возрастанию) и по ID (по убыванию).

Обратите внимание:

  • В каждом из трёх примеров ниже мы сначала объявляем пользовательскую функцию сравнения (alphSort, ageSort и idSort соответственно), а потом передаём её встроенной функции usort() в качестве обработчика массива.
  • Цикл foreach помогает по очереди перебирать карточки каждого сотрудника в главном массиве $employees. Для удобства мы в рамках цикла обзываем их $employee — то же самое английское слово в единственном числе.
  • Для доступа к нужным ключам вложенных массивов (карточек сотрудников) используется синтаксис с квадратными скобками: $array[«key»] и так далее.
echo "<h3>Сортировка сотрудников по ФИО через usort() и strcmp (по алфавиту)</h3>";
    function alphSort($name1, $name2) {
   	return strcmp($name1["ФИО"], $name2["ФИО"]);
     };
   	usort($employees, "alphSort");
   	foreach ($employees as $employee) {   	 
   	   echo "ID " . $employee["ID"] . ", " . "<b>ФИО: " . $employee["ФИО"] . ",</b> " . "Должность: " . $employee["Должность"] . ", " . "Возраст: " . $employee["Возраст"] . "<br>";
   	};

Функция alphSort() принимает по два значения ФИО ($name1 и $name2) и сравнивает их как строки с помощью встроенной функции strcmp(). Она передаётся во встроенную функцию usort(), где и применяется на нашем массиве.

Вывод отсортированного массива карточек сотрудников компании. Вариант первый — ФИО по алфавиту:

ID 2, ФИО: Ахрюнов Алексей Степанович, Должность: Бухгалтер, Возраст: 32
ID 4, ФИО: Бокакин Арсений Брониславович, Должность: Менеджер, Возраст: 31
ID 1, ФИО: Вувузела Андрей Павлович, Должность: Менеджер, Возраст: 29
ID 5, ФИО: Голохрюхин Евгений Владимирович, Должность: Директор, Возраст: 40
ID 3, ФИО: Охрюненко Борис Гориславович, Должность: Курьер, Возраст: 22
ID 6, ФИО: Совакошка Мария Игоревна, Должность: Старший инженер, Возраст: 26

Следующие два примера строятся по похожему принципу. Вот код для сортировки массива карточек сотрудников компании. Вариант второй — по возрасту.

echo "<h3>Сортировка сотрудников по возрасту через usort() (по возрастанию)</h3>";
   	function ageSort($age1, $age2) {
   		if ($age1["Возраст"] == $age2["Возраст"]) {
   		  return 0;
   		}
   		return ($age1["Возраст"] < $age2["Возраст"]) ? -1 : 1;
   		};   	 
   	usort($employees, "ageSort");
   	foreach ($employees as $employee) {   	 
   	     echo "ID " . $employee["ID"] . ", " . "ФИО: " . $employee["ФИО"] . ", " . "Должность: " . $employee["Должность"] . ", " . "<b>Возраст: " . $employee["Возраст"] . "</b><br>";
        };

Функция ageSort() должна сравнивать по два значения возраста сотрудников (в данном примере — $age1, $age2), и возвращать результат (отсортированный массив) в зависимости от результата сравнения. Она также передаётся во встроенную функцию usort().

Вывод отсортированного массива карточек сотрудников компании. Вариант второй — по возрасту:

ID 3, ФИО: Охрюненко Борис Гориславович, Должность: Курьер, Возраст: 22
ID 6, ФИО: Совакошка Мария Игоревна, Должность: Старший инженер, Возраст: 26
ID 1, ФИО: Вувузела Андрей Павлович, Должность: Менеджер, Возраст: 29
ID 4, ФИО: Бокакин Арсений Брониславович, Должность: Менеджер, Возраст: 31
ID 2, ФИО: Ахрюнов Алексей Степанович, Должность: Бухгалтер, Возраст: 32
ID 5, ФИО: Голохрюхин Евгений Владимирович, Должность: Директор, Возраст: 40

Код для сортировки массива карточек сотрудников компании. Вариант третий — по ID:

echo "<h3>Сортировка сотрудников по ID через usort() (по убыванию)</h3>";
   	function idSort($id1, $id2) {
   		if ($id1["ID"] == $id2["ID"]) {
   			return 0;
   	        }
   		return ($id1["ID"] < $id2["ID"]) ? 1 : -1;
   	 };   	 
   	 usort($employees, "idSort");
   	 foreach ($employees as $employee) {   	 
   	     echo "<b>ID " . $employee["ID"] . ",</b> " . "ФИО: " . $employee["ФИО"] . ", " . "Должность: " . $employee["Должность"] . ", " . "Возраст: " . $employee["Возраст"] . "<br>";
   	 };

?>

Аналогично прошлому примеру, здесь функция idSort() тоже заточена на сравнение по двум значениям — теперь это ID сотрудников ($id1, $id2) — и возвращает результат (отсортированный массив) в зависимости от результата сравнения.

Вывод отсортированного массива карточек сотрудников компании. Вариант третий — по ID:

ID6, ФИО: Совакошка Мария Игоревна, Должность: Старший инженер, Возраст: 26
ID 5, ФИО: Голохрюхин Евгений Владимирович, Должность: Директор, Возраст: 40
ID 4, ФИО: Бокакин Арсений Брониславович, Должность: Менеджер, Возраст: 31
ID 3, ФИО: Охрюненко Борис Гориславович, Должность: Курьер, Возраст: 22
ID 2, ФИО: Ахрюнов Алексей Степанович, Должность: Бухгалтер, Возраст: 32
ID 1, ФИО: Вувузела Андрей Павлович, Должность: Менеджер, Возраст: 29

Итоги

Мы рассмотрели основные виды сортировок массивов в PHP: числовую, алфавитную, естественную, многомерную и пользовательскую. Для всего этого мы нашли подходящие функции.

Для более детального знакомства с функциями сортировки массивов в PHP рекомендуем пользоваться таблицами-напоминалками: в разных руководствах они сделаны по-разному, поэтому лучше найти ту табличку, которая будет удобна именно вам. А для синтаксически правильного применения советуем пользоваться официальной документацией языка, тем более она переведена на русский.

Нейросети для работы и творчества!
Хотите разобраться, как их использовать? Смотрите конференцию: четыре топ-эксперта, кейсы и практика. Онлайн, бесплатно. Кликните для подробностей.
Смотреть программу
Понравилась статья?
Да

Пользуясь нашим сайтом, вы соглашаетесь с тем, что мы используем cookies 🍪

Ссылка скопирована