How to Sort Natural Order Strings in PHP
When working with strings containing numbers in PHP, we often need to sort them in a natural order that respects the numerical value of the digits. For example,
When you sort strings that contain numbers in PHP, the default alphabetical sort often produces results that feel "wrong" to a human reader. PHP's natsort() function fixes this by sorting an array using a natural order algorithm — the same way a person would order file1, file2, file10 instead of file1, file10, file2.
This page covers what natural order sorting is, how natsort() works (including the fact that it preserves keys), how it differs from sort(), how to handle case, and the common gotchas.
What is natural order sorting?
Natural order sorting (also called alphanumeric sorting) treats runs of digits inside a string as a single number rather than as individual characters. With a plain alphabetical sort, "100" comes before "2" because the comparison stops at the first character and '1' is less than '2' in the ASCII table. Natural order sorting instead compares 100 and 2 as numbers, so 2 correctly comes first.
This matters whenever your strings mix text and numbers — file names (img10.png), version labels (v2.13), or items like "10 apples" and "2 oranges".
Syntax
natsort(array &$array): truenatsort() takes the array by reference, sorts it in place, and (as of PHP 8.2) always returns true. In older versions the return type is bool. Because the array is modified directly, you do not assign the result back — you read the original variable after the call.
How to use the natsort() function
Compare the natural order against a regular alphabetical sort():
$fruits = array("10 apples", "2 oranges", "100 bananas");
natsort($fruits);
print_r($fruits);Output:
Array
(
[1] => 2 oranges
[0] => 10 apples
[2] => 100 bananas
)Notice the original keys (1, 0, 2) are kept and moved with their values — natsort() is a key-preserving sort, just like asort(). If you ran the plain sort() instead, you would get the alphabetical (and reindexed) result:
Array
(
[0] => 10 apples
[1] => 100 bananas
[2] => 2 oranges
)Here "100 bananas" lands in the middle because sort() compares it character by character.
Sorting file-like names
The classic use case is ordering file names that end in numbers:
$files = array("file20", "file3", "file1");
natsort($files);
print_r($files);Output:
Array
(
[2] => file1
[1] => file3
[0] => file20
)A regular sort would place file20 before file3 — rarely what you want when listing files.
natsort() is case-sensitive
natsort() compares uppercase letters before lowercase ones (uppercase ASCII codes are lower). Mixed-case input therefore groups capitals first:
$images = array("img12", "img10", "IMG2", "img1");
natsort($images);
print_r($images);Output:
Array
(
[2] => IMG2
[3] => img1
[1] => img10
[0] => img12
)IMG2 sorts ahead of the lowercase names. When case should be ignored, use the case-insensitive variant natcasesort():
$images = array("img12", "img10", "IMG2", "img1");
natcasesort($images);
print_r($images);Output:
Array
(
[3] => img1
[2] => IMG2
[1] => img10
[0] => img12
)Caveats and limitations
- Keys are preserved. If you need a clean, zero-based index afterwards, run
array_values($array)once the sort is done. - It sorts in place. The array is passed by reference; don't write
$x = natsort($arr)— that stores the boolean return value, not the sorted array. - Case-sensitive by default. Reach for
natcasesort()when case shouldn't affect order. - Arrays only.
natsort()does not work on strings or objects. To order a delimited string,explode()it into an array, sort, thenimplode()back. - Pairwise comparison. Under the hood it uses the same logic as
strnatcmp(); for a custom rule, sort withusort()and your own comparator.
Conclusion
natsort() sorts an array in human-friendly natural order, treating embedded numbers as numeric values while preserving the array's keys. Use it for file names, version strings, and any list mixing text with numbers — switch to natcasesort() when case shouldn't matter, and remember to reindex with array_values() if you need sequential keys. For other ordering needs, explore the related array sorting functions.