Hi, Just as a speed note! It's faster to calculate a square and find those records and then drop the corners with the circle calculation.
Scott. > -----Original Message----- > From: Eamon Daly [mailto:[EMAIL PROTECTED] > Sent: Tuesday, April 19, 2005 11:20 AM > To: Scott Haneda; MySql > Subject: Re: zip code search within x miles > > > I don't think anyone's replied with an actual great circle > calculation. Here's our zipcode table, populated with data > from zipcodedownload.com (and note the index on zipcode, > latitude, and longitude: > > CREATE TABLE `zipcodes` ( > `zipcode` char(5) NOT NULL default '', > `zipcode_type` enum('S','P','U','M') NOT NULL default 'S', > `city` char(45) NOT NULL default '', > `city_type` enum('D','A','N') NOT NULL default 'D', > `state` char(75) NOT NULL default '', > `state_code` char(2) NOT NULL default '', > `area_code` char(3) default NULL, > `latitude` double(12,6) NOT NULL default '0.000000', > `longitude` double(12,6) NOT NULL default '0.000000', > KEY `city_state_code` (`zipcode`,`city`,`state_code`), > KEY `position` (`zipcode`,`latitude`,`longitude`) > ) TYPE=MyISAM > > Here's the calculation to get zipcodes within 5 miles of > 02134: > > SELECT > b.zipcode, b.state, > (3956 * (2 * ASIN(SQRT( > POWER(SIN(((a.latitude-b.latitude)*0.017453293)/2),2) + > COS(a.latitude*0.017453293) * > COS(b.latitude*0.017453293) * > POWER(SIN(((a.longitude-b.longitude)*0.017453293)/2),2) > )))) AS distance > FROM zipcodes a, zipcodes b, zipcodes c > WHERE > a.zipcode = '02134' AND # <-- Your starting zipcode > a.zipcode = c.zipcode AND > (3956 * (2 * ASIN(SQRT( > POWER(SIN(((a.latitude-b.latitude)*0.017453293)/2),2) + > COS(a.latitude*0.017453293) * > COS(b.latitude*0.017453293) * > POWER(SIN(((a.longitude-b.longitude)*0.017453293)/2),2) > )))) <= 5 # <-- Your target radius > GROUP BY distance > > Takes about half a second on our box. Here's the explain: > > *************************** 1. row *************************** > table: a > type: ref > possible_keys: city_state_code,position,default_city > key: position > key_len: 5 > ref: const > rows: 2 > Extra: Using where; Using index; Using temporary; Using filesort > *************************** 2. row *************************** > table: c > type: ref > possible_keys: city_state_code,position,default_city > key: position > key_len: 5 > ref: const > rows: 2 > Extra: Using where; Using index > *************************** 3. row *************************** > table: b > type: ALL > possible_keys: NULL > key: NULL > key_len: NULL > ref: NULL > rows: 70443 > Extra: Using where > > In case you're curious about the number of zipcodes: > > mysql> select count(*), count(distinct zipcode) from zipcodes; > +----------+-------------------------+ > | count(*) | count(distinct zipcode) | > +----------+-------------------------+ > | 70443 | 42471 | > +----------+-------------------------+ > > Can't take credit for the SQL, by the way; I'm pretty sure I > found it on Google. > > ____________________________________________________________ > Eamon Daly > > > > ----- Original Message ----- > From: "Scott Haneda" <[EMAIL PROTECTED]> > To: "MySql" <mysql@lists.mysql.com> > Sent: Friday, April 15, 2005 5:37 PM > Subject: zip code search within x miles > > > > How are sites doing the search by zip and coming up with > results within x > > miles? Is there some OSS zip code download that has been created for > > this? > > > -- > MySQL General Mailing List > For list archives: http://lists.mysql.com/mysql > To unsubscribe: http://lists.mysql.com/[EMAIL PROTECTED] > -- MySQL General Mailing List For list archives: http://lists.mysql.com/mysql To unsubscribe: http://lists.mysql.com/[EMAIL PROTECTED]