Forum Moderators: coopster

Message Too Old, No Replies

Sort 2D Array

         

username

4:34 am on Jul 10, 2009 (gmt 0)

10+ Year Member Top Contributors Of The Month



Hi,

I need to sort a 2D array by some date stamps which are in the index. I need to sort by the values at [x][1]. Does anyone have any efficient code for doing this?

$myarray[0][0] = "one";
$myarray[0][1] = "2009-04-11";
$myarray[0][2] = "end01";

$myarray[1][0] = "two";
$myarray[1][1] = "2010-04-11";
$myarray[1][2] = "end02";

$myarray[2][0] = "three";
$myarray[2][1] = "2006-04-11";
$myarray[2][2] = "end03";

Thanks in advance.

coopster

1:34 pm on Jul 10, 2009 (gmt 0)

WebmasterWorld Administrator 10+ Year Member



Sorting an array by a subarray value [webmasterworld.com] has some discussion with a link to this thread that has code examples:

[webmasterworld.com...]

andrewsmd

4:43 pm on Jul 10, 2009 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member



Nothing bothers me more than when someone posts links. You post on here to get help, not to look at generic content. Try this note: i sorted by oldest first read my comments if you want the most recent first

$myarray = array();

$myarray[0][0] = "one";
$myarray[0][1] = "2009-04-11";
$myarray[0][2] = "end01";

$myarray[1][0] = "two";
$myarray[1][1] = "2010-04-11";
$myarray[1][2] = "end02";

$myarray[2][0] = "three";
$myarray[2][1] = "2006-04-11";
$myarray[2][2] = "end03";

$sortedArr = sortArray($myarray);

//this function takes in a 2d array
//and sorts it based on the second sub of the
//second dimension i.e. array[0][1] array[1][1] array[2][1]
function sortArray($array){

//a temp array to store all of the data
$tempArr = array();

foreach($array as $key => $i){

foreach ($i as $key2 => $j){

if($key2 == 1){

//push the values to sort
//into an array
array_push($tempArr, $j);

}//if

}//foreach $i

}//foreach array

//sort the temp array by oldest first
//if you want the most recent date first
//then comment asort($tempArr); and uncomment
//the line after it
asort($tempArr);
//arsort($tempArr);

//the array to return
$returnArr = array();

//now go through the temp array
foreach($tempArr as $key => $i){

foreach($array as $key2 => $j){

//if that date is in this array then we will
//add it to the return array
if(array_search($i, $j)){

array_push($returnArr, $j);

}//if array_search

}//foreach array

}//foreach tempArr

return($returnArr);

}//sortArray

username

11:05 pm on Jul 10, 2009 (gmt 0)

10+ Year Member Top Contributors Of The Month



Thanks andrewsmd, almost there. Strangely enough this solution only returns the first set of values in the sorted array, not the entire array ordered. See:

/* Print Array */
for($j=0;$j<3;$j++){
echo $sortedArr[$j][1];
echo "<br/>";
}

This prints:
2006-04-11

Any ideas?

andrewsmd

11:10 pm on Jul 10, 2009 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member



You need to put that in a double for because right now your only printing the first set. Plus, use a foreach they are much easier
//this just goes through the first array
foreach($sortedArr as $i){

//$i is going to be another array within the first one
//so we loop through it as well
foreach($i as $j){
echo("$j<br>");
}//foreach $i

}//foreach sortedArr

Try that.

andrewsmd

11:18 pm on Jul 10, 2009 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member



Maybe you don't understand foreaches now that I think about it so I'll explain it a little
Basically a foreach says for each item in this array do something then when you set the value $i it says this item will be called $i check out this example

$arr = array("keyOne" => "valueOne", "keyTwo" => "valueTwo");

//This creates an array that looks something like this
//$arr["keyOne"] = "valueOne";
//$arr["keyTwo] = "valueTwo";

/*In PHP you can assign your own keys if you want so you don't have to use the generic 1,2,3 for keys it becomes helpful once you understand it. Anyways that foreach on that loop*/
foreach($arr as $i){

//this says that for each value in
//$arr we will do something. in addition
//$i will be the current value of that array
//so if we echo $i we get the value
echo("$i<br>");

}

//you can also get the keys like this
foreach($arr as $key => $i){

//now we can see the key too
echo("Key: $key and its value is $i<br>");

}

Try that code out and see if it helps you understand arrays a little better.

andrewsmd

11:22 pm on Jul 10, 2009 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member



One last thing in your code if you did this
for($j=0;$j<3;$j++){
echo $sortedArr[$j][1];
echo $sortedArr[$j][2];
echo $sortedArr[$j][3];
echo "<br/>";
}
That would work but it's not dynamic if either of your arrays grow larger than that then you would miss some data use my foreaches in the first reply to your last thread

StoutFiles

12:08 am on Jul 11, 2009 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member



Nothing bothers me more than when someone posts links.

The mod did that so the OP would have to learn something, not be hand-fed the answer. I understand helping directly when they've made an effort and present what they've tried to do but "I need code for this, do it for me"...well, nothing bothers ME more.

username

9:31 am on Jul 11, 2009 (gmt 0)

10+ Year Member Top Contributors Of The Month



Thanks, but even when using the code below to print, it still only prints one results set because the code seems to be flawed somewhere.

foreach($sortedArr as $x){
foreach($x as $j){
echo("$j<br>");
}
}

This version works fine, but is there a less data intensive version? Probably not needed?

$myarray = array();

$myarray[0][0] = "one";
$myarray[0][1] = "2008-04-11";
$myarray[0][2] = "end01";

$myarray[1][0] = "two";
$myarray[1][1] = "2009-04-11";
$myarray[1][2] = "end02";

$myarray[2][0] = "three";
$myarray[2][1] = "2006-04-11";
$myarray[2][2] = "end03";

for($j=0;$j<2;$j++){
$date = $myarray[$j][1];
for($x=1;$x<3;$x++){
$date_tmp = $myarray[$x][1];
if($date < $date_tmp){

$tmp[0] = $myarray[$j][0];
$tmp[1] = $myarray[$j][1];
$tmp[2] = $myarray[$j][2];

$myarray[$j][0] = $myarray[$x][0];
$myarray[$j][1] = $myarray[$x][1];
$myarray[$j][2] = $myarray[$x][2];

$myarray[$x][0] = $tmp[0];
$myarray[$x][1] = $tmp[1];
$myarray[$x][2] = $tmp[2];
}
}
}

/* Print Results */
for($x=0;$x<3;$x++){
echo $myarray[$x][1];
echo "<br>";
}

andrewsmd

1:43 am on Jul 13, 2009 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member



Your still not printing the results right. Please use a foreach loop also, it makes things easier. Change /*Print Results*/ to
foreach($myarray as $i){

foreach($i as $j){

echo("$j<br>");

}

}
Also, the code I posted works fine try and use it.

$myarray = array();

$myarray[0][0] = "one";
$myarray[0][1] = "2009-04-11";
$myarray[0][2] = "end01";

$myarray[1][0] = "two";
$myarray[1][1] = "2010-04-11";
$myarray[1][2] = "end02";

$myarray[2][0] = "three";
$myarray[2][1] = "2006-04-11";
$myarray[2][2] = "end03";

$sortedArr = sortArray($myarray);

//print out the data
foreach($sortedArr as $i){

foreach($i as $j){

echo("$j<br>");

}

}

//this function takes in a 2d array
//and sorts it based on the second sub of the
//second dimension i.e. array[0][1] array[1][1] array[2][1]
function sortArray($array){

//a temp array to store all of the data
$tempArr = array();

foreach($array as $key => $i){

foreach ($i as $key2 => $j){

if($key2 == 1){

//push the values to sort
//into an array
array_push($tempArr, $j);

}//if

}//foreach $i

}//foreach array

//sort the temp array by oldest first
//if you want the most recent date first
//then comment asort($tempArr); and uncomment
//the line after it
asort($tempArr);
//arsort($tempArr);

//the array to return
$returnArr = array();

//now go through the temp array
foreach($tempArr as $key => $i){

foreach($array as $key2 => $j){

//if that date is in this array then we will
//add it to the return array
if(array_search($i, $j)){

array_push($returnArr, $j);

}//if array_search

}//foreach array

}//foreach tempArr

return($returnArr);

}//sortArray

Nutter

2:15 am on Jul 13, 2009 (gmt 0)

10+ Year Member



That seems like an awfully lot of code. How 'bout usort - [us2.php.net...] . Then you just modify the cmp() function that's given on that page.

function cmp($a, $b)
{
if ($a[1] == $b[1]) {
return 0;
}
return ($a[1] < $b[1]) ? -1 : 1;
}

coopster

12:12 pm on Jul 13, 2009 (gmt 0)

WebmasterWorld Administrator 10+ Year Member



That's exactly what is in the posted links I left in the initial response.

Nothing bothers me more than when someone posts links. You post on here to get help, not to look at generic content.

Please take the time to follow the links and actually read what is on the pages and you will not only find answers and even working code, but explanations as well.