views:

64

answers:

1

I am trying to output results of 2 sql queries to one JSON file. The problem is that I would like to order them ascending by distance which is the result of equation that takes homelat and homelon from the users table and lat, lng from locations table.(basically it takes lattitude and longitude of one point and another and computes the distance between these points). Is it possible to take some parameters from both select queries, compute it and output the result in ascending order?

$wynik = mysql_query("SELECT homelat, homelon FROM users WHERE guid='2'") or 
die(mysql_error()); ;

$query = "SELECT * FROM locations WHERE timestamp";
$result = map_query($query);
$points = array();

while ($aaa = mysql_fetch_assoc($wynik)) {

while ($row = mysql_fetch_array($result, MYSQL_ASSOC)) {

    array_push($points, array('name'=>$row['name'], 'lat'=>$row['lat'], 
'lng'=>$row['lng'], 'description'=>$row['description'], 
'eventType'=>$row['eventType'], 'date'=>$row['date'],
        'isotime'=>date('c', ($row['timestamp'])), 'homelat'=>$aaa['homelat'], 
'homelon'=>$aaa['homelon']));

}
echo json_encode(array("Locations"=>$points));
+1  A: 

So the resulting array should be something like:

'name' => 'something',
'lat' => 'something',
'lng' => 'something',
'description' => 'something',
etc.

Use usort to sort it.

usort($array, 'sortByOption');
function sortByOption($a, $b) {
  $distA = dist($a['homelat'], $a['homelong'], $a['lat'], $a['long']);
  $distB = dist($b['homelat'], $b['homelong'], $b['lat'], $b['long']);
  return strcmp($distA, $distB);
}
function dist($x1, $y1, $x2, $y2) {
  return pow($x2 - $x1, 2) + pow($y2 - $y1, 2);
}

EDIT: Sorry, didn't 100% read your question. Revised for the solution (though not a great one). You should be calculating distance in the array itself. And to save time, don't do the square-root.

EDIT 2: Final result.

while ($aaa = mysql_fetch_assoc($wynik)) {
  while ($row = mysql_fetch_array($result, MYSQL_ASSOC)) {
    array_push($points, array('name'=>$row['name'], 
                               'lat'=>$row['lat'], 
                               'lng'=>$row['lng'], 
                       'description'=>$row['description'], 
                         'eventType'=>$row['eventType'],
                              'date'=>$row['date'],
                           'isotime'=>date('c', ($row['timestamp'])), 
                           'homelat'=>$aaa['homelat'], 
                           'homelon'=>$aaa['homelon'],
                          'dist'=>dist($aaa['homelat'], $aaa['homelon'], $row['lat'], $row['lng'])
    ));
  }
}
usort($points, 'sortByDist'); // This sorts the points!
echo json_encode(array("Locations"=>$points));
function sortByDist($a, $b) {
  return strcmp($a['dist'], $b['dist']);
}
function dist($x1, $y1, $x2, $y2) {
  return pow($x2 - $x1, 2) + pow($y2 - $y1, 2);
}
St. John Johnson
Right. Should I place your code just before echo json_encode?
Vafello
Yes, except the functions can go anywhere. To save calculation time, you should calculate the distance as you save the array. So in the array_push, store the dist() thing in there. And then the usort should only sort on the $a['dist'] and $b['dist']. I'll edit to show you what I mean.
St. John Johnson
Awesome, thank you.
Vafello
I have one more question. Your code works fine, but how actually make it return the array sorted ascending?It doesn't sort the json output, it just calculates the distance.
Vafello
Well, it should be. That's what the usort() is for. OH! My usort is taking the wrong parameter, it should be usort(**$points**, 'soryByDist'); ***facepalm*** Sorry.
St. John Johnson
It works now, there was a typo in return strcmp($a['dist'], $a['dist']); It should be $b not $a. Thanks a lot. You saved me a lot of time:)
Vafello
By accident I down voted your answer(I wanted to vote it up again and it failed). I can upvote it if you edit the answer (change a to b) and I will vote it up again. Thanks again.
Vafello
Haha, fair enough. Changed it.
St. John Johnson