HeidiR Posted October 6, 2008 Share Posted October 6, 2008 Hello all, I'm trying to use array_multisort with a 2d array (code below). I have a simple example below which produces the following incorrect results: 0) b -> 2 1) a -> 1 2) c -> 3 0) 2 -> b 1) 1 -> a 2) c -> 3 Note: This example is similar to example #2 on php.net but it doesn't seem to work as advertised. What am I missing??? Thanks, HeidiR <?php $ar[0][0] = "b"; $ar[1][0] = "a"; $ar[2][0] = "c"; $ar[0][1] = "2"; $ar[1][1] = "1"; $ar[2][1] = "3"; for($i = 0; $i <= count($ar) -1; $i++) { echo ($i . ") " . $ar[$i][0] . " -> " . $ar[$i][1] . "<br />"); } echo ("<br />"); array_multisort($ar[0], SORT_ASC, SORT_STRING, $ar[1], SORT_ASC, SORT_STRING); for($i = 0; $i <= count($ar) -1; $i++) { echo ($i . ") " . $ar[$i][0] . " -> " . $ar[$i][1] . "<br />"); } ?> Link to comment https://forums.phpfreaks.com/topic/127237-array_multisort-with-2d-array/ Share on other sites More sharing options...
genericnumber1 Posted October 6, 2008 Share Posted October 6, 2008 If they're already linked in the array, just use usort() to sort the values you want and the other one will come along for the ride... This should work... (basically copied/pasted from the php manual http://us2.php.net/usort ) function cmp($a, $b) { strcmp($a[0], $b[0]); } $ar[0][0] = "b"; $ar[1][0] = "a"; $ar[2][0] = "c"; $ar[0][1] = "2"; $ar[1][1] = "1"; $ar[2][1] = "3"; usort($ar, "cmp"); print_r($ar); Link to comment https://forums.phpfreaks.com/topic/127237-array_multisort-with-2d-array/#findComment-658156 Share on other sites More sharing options...
HeidiR Posted October 6, 2008 Author Share Posted October 6, 2008 If they're already linked in the array, just use usort() to sort the values you want and the other one will come along for the ride... This should work... (basically copied/pasted from the php manual http://us2.php.net/usort ) function cmp($a, $b) { strcmp($a[0], $b[0]); } $ar[0][0] = "b"; $ar[1][0] = "a"; $ar[2][0] = "c"; $ar[0][1] = "2"; $ar[1][1] = "1"; $ar[2][1] = "3"; usort($ar, "cmp"); print_r($ar); Thanks for the quick reply and solution. This works great for string arrays. I have extended your example and created another function to handle sorting a 2d array with numeric values. The usort and _ncmp functions below sort the numeric values correctly. usort($ar, '_ncmp') function _ncmp($a, $b) { if($a[0] < $b[0]) //col1 return -1; else return 1; } Is there a way to call _ncmp from usort with an argument to dynamically change the sort column? Something like: function _ncmp($a, $b, $sort_col) { if($sort_col] < $b[$sort_col]) return -1; else return 1; } Link to comment https://forums.phpfreaks.com/topic/127237-array_multisort-with-2d-array/#findComment-658224 Share on other sites More sharing options...
genericnumber1 Posted October 6, 2008 Share Posted October 6, 2008 it would be easiest to just change the cmp function to <?php function cmp($a, $b) { return strnatcmp($a[0], $b[0]); } ?> As for passing params to the function called by usort? It might be cleanest if you implement it in a class... <?php class OrderedMDArray { private $array; private $sortKey; public function __construct($array, $sortKey) { $this->array = $array; $this->sortKey = $sortKey; } public function get() { usort($this->array, array($this, 'cmp')); return $this->array; } private function cmp($str1, $str2) { return strnatcmp($str1[$this->sortKey], $str2[$this->sortKey]); } } $ar[0][0] = "b"; $ar[1][0] = "a"; $ar[2][0] = "c"; $ar[0][1] = "2"; $ar[1][1] = "1"; $ar[2][1] = "3"; $ordArray = new OrderedMDArray($ar, 0); print_r($ordArray->get()); ?> but you can also do it with the global keyword (I hate the global keyword)... <?php function cmp($a, $b) { global $key; return strnatcmp($a[$key], $b[$key]); } $ar[0][0] = "b"; $ar[1][0] = "a"; $ar[2][0] = "c"; $ar[0][1] = "2"; $ar[1][1] = "1"; $ar[2][1] = "3"; $key = 0; usort($ar, "cmp"); print_r($ar); ?> PS. sorry, forgot the return before the strcmp() in my first reply. Link to comment https://forums.phpfreaks.com/topic/127237-array_multisort-with-2d-array/#findComment-658248 Share on other sites More sharing options...
HeidiR Posted October 6, 2008 Author Share Posted October 6, 2008 it would be easiest to just change the cmp function to <?php function cmp($a, $b) { return strnatcmp($a[0], $b[0]); } ?> As for passing params to the function called by usort? It might be cleanest if you implement it in a class... <?php class OrderedMDArray { private $array; private $sortKey; public function __construct($array, $sortKey) { $this->array = $array; $this->sortKey = $sortKey; } public function get() { usort($this->array, array($this, 'cmp')); return $this->array; } private function cmp($str1, $str2) { return strnatcmp($str1[$this->sortKey], $str2[$this->sortKey]); } } $ar[0][0] = "b"; $ar[1][0] = "a"; $ar[2][0] = "c"; $ar[0][1] = "2"; $ar[1][1] = "1"; $ar[2][1] = "3"; $ordArray = new OrderedMDArray($ar, 0); print_r($ordArray->get()); ?> but you can also do it with the global keyword (I hate the global keyword)... <?php function cmp($a, $b) { global $key; return strnatcmp($a[$key], $b[$key]); } $ar[0][0] = "b"; $ar[1][0] = "a"; $ar[2][0] = "c"; $ar[0][1] = "2"; $ar[1][1] = "1"; $ar[2][1] = "3"; $key = 0; usort($ar, "cmp"); print_r($ar); ?> PS. sorry, forgot the return before the strcmp() in my first reply. Thanks for the information. I'll give them a try. HeidiR Link to comment https://forums.phpfreaks.com/topic/127237-array_multisort-with-2d-array/#findComment-658362 Share on other sites More sharing options...
Recommended Posts
Archived
This topic is now archived and is closed to further replies.