mirror of
https://github.com/kevin-DL/services.git
synced 2026-01-11 19:04:35 +00:00
53 lines
1.6 KiB
Go
53 lines
1.6 KiB
Go
package handler
|
|
|
|
import (
|
|
"fmt"
|
|
"math"
|
|
|
|
pb "github.com/micro/services/routes/proto"
|
|
)
|
|
|
|
func toRadians(num float64) float64 {
|
|
return num * math.Pi / float64(180)
|
|
}
|
|
|
|
// calcDistance calculates the distance between two points using the "haversine" formula.
|
|
// The formula is based on http://mathforum.org/library/drmath/view/51879.html.
|
|
func calcDistance(p1 *pb.Point, p2 *pb.Point) int32 {
|
|
const CordFactor float64 = 1e7
|
|
const R = float64(6371000) // earth radius in metres
|
|
lat1 := toRadians(float64(p1.Latitude) / CordFactor)
|
|
lat2 := toRadians(float64(p2.Latitude) / CordFactor)
|
|
lng1 := toRadians(float64(p1.Longitude) / CordFactor)
|
|
lng2 := toRadians(float64(p2.Longitude) / CordFactor)
|
|
dlat := lat2 - lat1
|
|
dlng := lng2 - lng1
|
|
|
|
a := math.Sin(dlat/2)*math.Sin(dlat/2) +
|
|
math.Cos(lat1)*math.Cos(lat2)*
|
|
math.Sin(dlng/2)*math.Sin(dlng/2)
|
|
c := 2 * math.Atan2(math.Sqrt(a), math.Sqrt(1-a))
|
|
|
|
distance := R * c
|
|
return int32(distance)
|
|
}
|
|
|
|
func inRange(point *pb.Point, rect *pb.Rectangle) bool {
|
|
left := math.Min(float64(rect.Lo.Longitude), float64(rect.Hi.Longitude))
|
|
right := math.Max(float64(rect.Lo.Longitude), float64(rect.Hi.Longitude))
|
|
top := math.Max(float64(rect.Lo.Latitude), float64(rect.Hi.Latitude))
|
|
bottom := math.Min(float64(rect.Lo.Latitude), float64(rect.Hi.Latitude))
|
|
|
|
if float64(point.Longitude) >= left &&
|
|
float64(point.Longitude) <= right &&
|
|
float64(point.Latitude) >= bottom &&
|
|
float64(point.Latitude) <= top {
|
|
return true
|
|
}
|
|
return false
|
|
}
|
|
|
|
func serialize(point *pb.Point) string {
|
|
return fmt.Sprintf("%d %d", point.Latitude, point.Longitude)
|
|
}
|