Jump to content

[SOLVED] Distance Estimation, closest matches using Zip Codes


Stryves

Recommended Posts

I modified a script so that it calculates the distances between stores and a person, but it doesn't show closest stores first? I searched the boards and haven't found an answer for this, with so many store locators on the web I'm hoping someone knows where I am missing.

 

<?php

// our function to determine the distance

function distance($lat1, $lon1, $lat2, $lon2) {

  $theta = $lon1 - $lon2;
  $dist = sin(deg2rad($lat1)) * sin(deg2rad($lat2)) +  cos(deg2rad($lat1)) * cos(deg2rad($lat2)) * cos(deg2rad($theta));
  $dist = acos($dist);
  $dist = rad2deg($dist);
  $miles = $dist * 60 * 1.1515;
}

$userzip=$_POST['userzip'];

// User posts their Zip Code
// Next we find out their latitude and longitude

$query1="SELECT b.zip AS BZIP, a.zip AS AZIP, a.long AS ALONG, a.lat As ALAT FROM latlongcodes a JOIN users b ON b.zip='$userzip'";
$result1=mysql_query($query1) or die("Failed Query 1");
$sql1=mysql_fetch_array($result1);

// Assign Variables for their lat and long

$ulat=$sql1[ALAT]
$ulong=$sql1[ALONG]

// Now we grab all the stores and check their lat and long and display the distances

$query="SELECT b.shop AS BSHOP, b.zip AS BZIP, a.zip AS AZIP, a.long AS ALONG, a.lat AS ALAT FROM latlongcodes a JOIN shops b ON b.zip=a.zip LIMIT 10";
$result=mysql_query($query) or die("Failed Query 2");
while($sql=mysql_fetch_array($result))
{
  echo distance($ulat, $ulong, $sql[ALAT], $sql[ALONG]) . " miles to $sql[bSHOP]<br/>";
  }
?>

Works great, but I can't figure out how to get the while to display closest first.

Thank you for the reply.

 

I have tried using the ORDER BY, zip, lat, long... doesn't seem to take into the distance function output, only the order in the SQL query?

 

Missing array syntax is my bad habit, thank you for the reminder!

Oh, didn't notice how you were using the distance() function.  You may want to do something like:

 

<?php
while($sql=mysql_fetch_array($result)) {
  $distances[$sql['BSHOP']] = distance($ulat, $ulong, $sql['ALAT'], $sql['ALONG']);
}
natsort($distances);
foreach ($distances as $shop=>$distance) {
   echo "$distances miles to $shop<br />";
}

So close! This is what it now displays.

 

Array miles to Store 7

Array miles to Store 8

Array miles to Store 9

Array miles to Store 6

 

Technically distance wise it's accurate, but not sure why it's saying Array instead of the actual mileage.

 

This is my latest code, I stripped out the other stuff that's not required for this test.

 

<?php
function distance($lat1, $lon1, $lat2, $lon2, $unit) {

$theta = $lon1 - $lon2;
$dist = sin(deg2rad($lat1)) * sin(deg2rad($lat2)) +  cos(deg2rad($lat1)) * cos(deg2rad($lat2)) * cos(deg2rad($theta));
$dist = acos($dist);
$dist = rad2deg($dist);
$miles = $dist * 60 * 1.1515;
}

$userzip=90210;

$query1="SELECT b.shop as BSHOP, b.pzcode AS BZIP, b.country as BCOUNTRY, a.zip AS AZIP, a.long AS ALONG, a.lat As ALAT FROM latlongcodes a JOIN shops b ON a.zip='$userzip'";
$result1=mysql_query($query1) or die("Failed Query 1");
$sql1=mysql_fetch_array($result1);

$ulat=$sql1['ALAT'];
$ulong=$sql1['ALONG'];

$query="SELECT b.shop AS BSHOP, b.pzcode AS BZIP, a.zip AS AZIP, a.long AS ALONG, a.lat AS ALAT FROM latlongcodes a JOIN shops b ON b.pzcode=a.zip LIMIT 10";
$result=mysql_query($query) or die("Failed Query 2");
while($sql=mysql_fetch_array($result)) {
     $distances[$sql['BSHOP']] = distance($ulat, $ulong, $sql['ALAT'], $sql['ALONG']);
   }
   natsort($distances);
   foreach ($distances as $shop=>$distance) {
      echo "$distances miles to $shop<br />";
     }
?>

My bad.  I used $distances instead of $distance:

 

<?php
function distance($lat1, $lon1, $lat2, $lon2, $unit) {

$theta = $lon1 - $lon2;
$dist = sin(deg2rad($lat1)) * sin(deg2rad($lat2)) +  cos(deg2rad($lat1)) * cos(deg2rad($lat2)) * cos(deg2rad($theta));
$dist = acos($dist);
$dist = rad2deg($dist);
$miles = $dist * 60 * 1.1515;
}

$userzip=90210;

$query1="SELECT b.shop as BSHOP, b.pzcode AS BZIP, b.country as BCOUNTRY, a.zip AS AZIP, a.long AS ALONG, a.lat As ALAT FROM latlongcodes a JOIN shops b ON a.zip='$userzip'";
$result1=mysql_query($query1) or die("Failed Query 1");
$sql1=mysql_fetch_array($result1);

$ulat=$sql1['ALAT'];
$ulong=$sql1['ALONG'];

$query="SELECT b.shop AS BSHOP, b.pzcode AS BZIP, a.zip AS AZIP, a.long AS ALONG, a.lat AS ALAT FROM latlongcodes a JOIN shops b ON b.pzcode=a.zip LIMIT 10";
$result=mysql_query($query) or die("Failed Query 2");
while($sql=mysql_fetch_array($result)) {
     $distances[$sql['BSHOP']] = distance($ulat, $ulong, $sql['ALAT'], $sql['ALONG']);
   }
   natsort($distances);
   foreach ($distances as $shop=>$distance) {
      echo "$distance miles to $shop<br />";
     }
?>

 

Should work perfectly.

This is the output, sorry for the delay!

 

Array ( [8] => [9] => [10] => [11] => [7] => [6] => [2] => [3] => [4] => [5] => [1] => ) miles to 8

miles to 9

miles to 10

miles to 11

miles to 7

miles to 6

miles to 2

miles to 3

miles to 4

miles to 5

miles to 1

 

Ah!  The problem is that you don't actually return $miles from the distance() function, thereby filling the array with nothing.

 

Change distance()'s code to:

<?php
function distance($lat1, $lon1, $lat2, $lon2, $unit) {

$theta = $lon1 - $lon2;
$dist = sin(deg2rad($lat1)) * sin(deg2rad($lat2)) +  cos(deg2rad($lat1)) * cos(deg2rad($lat2)) * cos(deg2rad($theta));
$dist = acos($dist);
$dist = rad2deg($dist);
$miles = $dist * 60 * 1.1515;
return $miles;
}

Archived

This topic is now archived and is closed to further replies.

×
×
  • Create New...

Important Information

We have placed cookies on your device to help make this website better. You can adjust your cookie settings, otherwise we'll assume you're okay to continue.