public bool ContainsGeoHash(GeoHash hash) { var hashStr = hash.GetGeoHashString(); return(Compare(_startValue, hashStr, StringComparison.Ordinal) <= 0 && Compare(_endValue, hashStr, StringComparison.Ordinal) > 0); }
public static GeoHashQuery QueryForGeoHash(GeoHash geohash, int bits) { var hash = geohash.GetGeoHashString(); var precision = (int)Math.Ceiling((double)bits / Base32Utils.BitsPerBase32Char); if (hash.Length < precision) { return(new GeoHashQuery(hash, hash + "~")); } hash = hash.Substring(0, precision); var hashBase = hash.Substring(0, hash.Length - 1); var lastValue = Base32Utils.Base32CharToValue(hash[hash.Length - 1]); var significantBits = bits - hashBase.Length * Base32Utils.BitsPerBase32Char; var unusedBits = Base32Utils.BitsPerBase32Char - significantBits; // delete unused bits var startValue = (lastValue >> unusedBits) << unusedBits; var endValue = startValue + (1 << unusedBits); var startHash = hashBase + Base32Utils.ValueToBase32Char(startValue); var endHash = endValue > 31 ? hashBase + "~" : hashBase + Base32Utils.ValueToBase32Char(endValue); return(new GeoHashQuery(startHash, endHash)); }
public static HashSet <GeoHashQuery> QueriesAtLocation(GeoPoint location, double radius) { var queryBits = Math.Max(1, Utils.BitsForBoundingBox(location, radius)); var geoHashPrecision = (int)Math.Ceiling((float)queryBits / Base32Utils.BitsPerBase32Char); var latitude = location.Latitude; var longitude = location.Longitude; var latitudeDegrees = radius / Constants.MetersPerDegreeLatitude; var latitudeNorth = Math.Min(90, latitude + latitudeDegrees); var latitudeSouth = Math.Max(-90, latitude - latitudeDegrees); var longitudeDeltaNorth = GeoUtils.DistanceToLongitudeDegrees(radius, latitudeNorth); var longitudeDeltaSouth = GeoUtils.DistanceToLongitudeDegrees(radius, latitudeSouth); var longitudeDelta = Math.Max(longitudeDeltaNorth, longitudeDeltaSouth); var queries = new HashSet <GeoHashQuery>(); var geoHash = new GeoHash(latitude, longitude, geoHashPrecision); var geoHashW = new GeoHash(latitude, GeoUtils.WrapLongitude(longitude - longitudeDelta), geoHashPrecision); var geoHashE = new GeoHash(latitude, GeoUtils.WrapLongitude(longitude + longitudeDelta), geoHashPrecision); var geoHashN = new GeoHash(latitudeNorth, longitude, geoHashPrecision); var geoHashNw = new GeoHash(latitudeNorth, GeoUtils.WrapLongitude(longitude - longitudeDelta), geoHashPrecision); var geoHashNE = new GeoHash(latitudeNorth, GeoUtils.WrapLongitude(longitude + longitudeDelta), geoHashPrecision); var geoHashS = new GeoHash(latitudeSouth, longitude, geoHashPrecision); var geoHashSW = new GeoHash(latitudeSouth, GeoUtils.WrapLongitude(longitude - longitudeDelta), geoHashPrecision); var geoHashSE = new GeoHash(latitudeSouth, GeoUtils.WrapLongitude(longitude + longitudeDelta), geoHashPrecision); queries.Add(QueryForGeoHash(geoHash, queryBits)); queries.Add(QueryForGeoHash(geoHashE, queryBits)); queries.Add(QueryForGeoHash(geoHashW, queryBits)); queries.Add(QueryForGeoHash(geoHashN, queryBits)); queries.Add(QueryForGeoHash(geoHashNE, queryBits)); queries.Add(QueryForGeoHash(geoHashNw, queryBits)); queries.Add(QueryForGeoHash(geoHashS, queryBits)); queries.Add(QueryForGeoHash(geoHashSE, queryBits)); queries.Add(QueryForGeoHash(geoHashSW, queryBits)); // Join queries bool didJoin; do { GeoHashQuery query1 = null; GeoHashQuery query2 = null; foreach (var query in queries) { foreach (var other in queries.Where(other => query != other && query.CanJoinWith(other))) { query1 = query; query2 = other; break; } } if (query1 != null && query2 != null) { queries.Remove(query1); queries.Remove(query2); queries.Add(query1.JoinWith(query2)); didJoin = true; } else { didJoin = false; } } while (didJoin); return(queries); }