natcasesort

(PHP 4, PHP 5)

natcasesort --  用“自然排序”算法对数组进行不区分大小写字母的排序

说明

bool natcasesort ( array &array )

本函数实现了一个和人们通常对字母数字字符串进行排序的方法一样的排序算法并保持原有键/值的关联,这被称为“自然排序”。

如果成功则返回 TRUE,失败则返回 FALSE

natcasesort()natsort() 函数的不区分大小写字母的版本。

例子 1. natcasesort() 例子

<?php
$array1
= $array2 = array('IMG0.png', 'img12.png', 'img10.png', 'img2.png', 'img1.png', 'IMG3.png');

sort($array1);
echo
"Standard sorting\n";
print_r($array1);

natcasesort($array2);
echo
"\nNatural order sorting (case-insensitive)\n";
print_r($array2);
?>

上例将输出:

Standard sorting
Array
(
    [0] => IMG0.png
    [1] => IMG3.png
    [2] => img1.png
    [3] => img10.png
    [4] => img12.png
    [5] => img2.png
)

Natural order sorting (case-insensitive)
Array
(
    [0] => IMG0.png
    [4] => img1.png
    [3] => img2.png
    [5] => IMG3.png
    [2] => img10.png
    [1] => img12.png
)

更多信息见 Martin Pool 的 Natural Order String Comparison 页面。

参见 sort()natsort()strnatcmp()strnatcasecmp()


add a note add a note User Contributed Notes
php at method5 dot de
07-Nov-2003 02:56
hi all,
this is my first post at php.net first of all thank you for this huge site :)

ok i found it usefull to post this for others. in the german language we have words like '  ' its called "umlaute" and it was a problem to me to "naturally" sort an huge array correctly so i coded this small block to get me helped, if anyone has an better idea please post and let us know as i am not a real crack :)

1. change each "umlaut" () into its "nearest" equivalent
2. natcasesorting it naturally
3. re-assiging the correct sorted array with the original-words again while keeping track of the KEY...

example-array:
$aSupplier = array(3 => "MAN",2 => "Atlas",16 => "Chevrolet",17 => "Chrysler",19 => "Citroen",24 => "DAF",25 => "Daihatsu",27 => "Daewoo",28 => "Demag",30 => "Dodge",36 => "Schierling",208 => "HIAB",38 => "Hffermann",39 => "Gergen",40 => "Kubato",41 => "Faun",43 => "Kleindienst",44 => "Swing",45 => "Neuhaus",46 => "Unimog",47 => "Meiller",48 => "Pfau-Johnston",49 => "Geesink",50 => "Schrling",51 => "Demag-Witting",53 => "Helmers",54 => "Ellermann",55 => "Jacobsen",56 => "Biki",57 => "Hansa",58 => "Kramer",59 => "Schmitz",60 => "Toro",61 => "Iseki",62 => "Haller",63 => "Kuka",64 => "Brock",65 => "Ambross",66 => "Sobernheimer",67 => "Pietsch",68 => "Kpper",69 => "Weisser",71 => "Wackenhut");

foreach ( $aSupplier as $key => $value )
{
   $aSupplier2[$key] = strtr($aSupplier[$key], "", "AOUaous");
}   

natcasesort($aSupplier2);

foreach ( $aSupplier2 as $key => $value )
{
  if ( $aSupplier2[$key] != "" )
   $aSupplier3[$key] = $aSupplier[$key];
}   

echo "<pre>";
print_r($aSupplier3);
echo "</pre>";

greetz
tim
vbAlexDOSMan at Yahoo dot com
12-Sep-2003 04:21
Ulli at Stemmeler dot net:  I remade your function -- it's a little more compact now -- Enjoy...

function ignorecasesort(&$array) {

  /*Make each element it's lowercase self plus itself*/
  /*(e.g. "MyWebSite" would become "mywebsiteMyWebSite"*/
  for ($i = 0; $i < sizeof($array); $array[$i] = strtolower($array[$i]).$array[$i], $i++);

  /*Sort it -- only the lowercase versions will be used*/
  sort($array);

  /*Take each array element, cut it in half, and add the latter half to a new array*/
  /*(e.g. "mywebsiteMyWebSite" would become "MyWebSite")*/
  for ($i = 0; $i < sizeof($array); $i++) {
   $this = $array[$i];
   $array[$i] = substr($this, (strlen($this)/2), strlen($this));
  }
}
dslicer at maine dot rr dot com
03-Jun-2003 09:41
Something that should probably be documented is the fact that both natsort and natcasesort maintain the key-value associations of the array. If you natsort a numerically indexed array, a for loop will not produce the sorted order; a foreach loop, however, will produce the sorted order, but the indices won't be in numeric order. If you want natsort and natcasesort to break the key-value associations, just use array_values on the sorted array, like so:

natcasesort($arr);
$arr = array_values($arr);
tmiller25 at hotmail dot com
26-Apr-2002 10:55
add this loop to the function above if you want items which have the same first characters to be listed in a way that the shorter string comes first.
--------------------
  /* short before longer (e.g. 'abc' should come before 'abcd') */
  for($i=count($array)-1;$i>0;$i--) {
   $str_a = $array[$i  ];
   $str_b = $array[$i-1];
   $cmp_a = strtolower(substr($str_a,0,strlen($str_a)));
   $cmp_b = strtolower(substr($str_b,0,strlen($str_a)));
   if ($cmp_a==$cmp_b && strlen($str_a)<strlen($str_b)) {
     $array[$i]=$str_b; $array[$i-1]=$str_a; $i+=2;
   }
  }
--------------------
Ulli at Stemmeler dot net
06-Apr-2002 12:01
natcasesort didn't work first time I needed something like this.
Not on my local server, not on my server on the web.
I needed an array sorted ignoring upper and lower cases. In the end lower case array-members stayed at the end of the array.

I replaced it with this function:
---------
function ignorecasesort(&$array) {
$separator="|<>|";
for($i=0;$i<sizeof($array);$i++) { $array[$i]=strtolower($array[$i]).$separator.$array[$i]; }
sort($array);
for($i=0;$i<sizeof($array);$i++) { $this=$array[$i]; $this=explode($separator,$this); $array[$i]=$this[1]; }
}
---------