mirror of
https://codeberg.org/redict/redict.git
synced 2025-01-22 08:08:53 -05:00
GEOSEARCH BYBOX: Reduce wastefull computation on geohashGetDistanceIfInRectangle and geohashGetDistance (#11535)
Optimize geohashGetDistanceIfInRectangle when there are many misses. It calls 3x geohashGetDistance. The first 2 times we call them to produce intermediate results. This PR focus on optimizing for those 2 intermediate results. 1 Reduce expensive computation on intermediate geohashGetDistance with same long 2 Avoid expensive lon_distance calculation if lat_distance fails beforehand Co-authored-by: Oran Agra <oran@redislabs.com>
This commit is contained in:
parent
ca174e1d47
commit
ae1de54900
@ -225,8 +225,12 @@ double geohashGetDistance(double lon1d, double lat1d, double lon2d, double lat2d
|
|||||||
lon2r = deg_rad(lon2d);
|
lon2r = deg_rad(lon2d);
|
||||||
u = sin((lat2r - lat1r) / 2);
|
u = sin((lat2r - lat1r) / 2);
|
||||||
v = sin((lon2r - lon1r) / 2);
|
v = sin((lon2r - lon1r) / 2);
|
||||||
return 2.0 * EARTH_RADIUS_IN_METERS *
|
double a = u * u;
|
||||||
asin(sqrt(u * u + cos(lat1r) * cos(lat2r) * v * v));
|
/* if v == 0 we can avoid doing expensive math */
|
||||||
|
if (v != 0.0){
|
||||||
|
a += cos(lat1r) * cos(lat2r) * v * v;
|
||||||
|
}
|
||||||
|
return 2.0 * EARTH_RADIUS_IN_METERS * asin(sqrt(a));
|
||||||
}
|
}
|
||||||
|
|
||||||
int geohashGetDistanceIfInRadius(double x1, double y1,
|
int geohashGetDistanceIfInRadius(double x1, double y1,
|
||||||
@ -253,9 +257,14 @@ int geohashGetDistanceIfInRadiusWGS84(double x1, double y1, double x2,
|
|||||||
*/
|
*/
|
||||||
int geohashGetDistanceIfInRectangle(double width_m, double height_m, double x1, double y1,
|
int geohashGetDistanceIfInRectangle(double width_m, double height_m, double x1, double y1,
|
||||||
double x2, double y2, double *distance) {
|
double x2, double y2, double *distance) {
|
||||||
double lon_distance = geohashGetDistance(x2, y2, x1, y2);
|
/* latitude distance is less expensive to compute than longitude distance
|
||||||
|
* so we check first for the latitude condition */
|
||||||
double lat_distance = geohashGetDistance(x2, y2, x2, y1);
|
double lat_distance = geohashGetDistance(x2, y2, x2, y1);
|
||||||
if (lon_distance > width_m/2 || lat_distance > height_m/2) {
|
if (lat_distance > height_m/2) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
double lon_distance = geohashGetDistance(x2, y2, x1, y2);
|
||||||
|
if (lon_distance > width_m/2) {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
*distance = geohashGetDistance(x1, y1, x2, y2);
|
*distance = geohashGetDistance(x1, y1, x2, y2);
|
||||||
|
Loading…
Reference in New Issue
Block a user