@@ -1,5 +1,7 @@
package com.chaozhanggui.system.cashierservice.util ;
import java.math.BigDecimal ;
import java.math.RoundingMode ;
import java.util.HashMap ;
import java.util.Map ;
@@ -29,7 +31,7 @@ public class LocationUtils {
* @return 距离,单位千米(KM)
* @see <a href="https://zh.wikipedia.org/wiki/%E5%8D%8A%E6%AD%A3%E7%9F%A2%E5%85%AC%E5%BC%8F">半正矢(Haversine)公式</a>
*/
public static double getDistanceFrom2LngLat ( double lng1 , double lat1 , double lng2 , double lat2 ) {
public static BigDecimal getDistanceFrom2LngLat ( double lng1 , double lat1 , double lng2 , double lat2 ) {
//将角度转化为弧度
double radLng1 = radians ( lng1 ) ; //d * Math.PI / 180.0;
double radLat1 = radians ( lat1 ) ;
@@ -39,7 +41,10 @@ public class LocationUtils {
double a = radLat1 - radLat2 ;
double b = radLng1 - radLng2 ;
return 2 * asin ( sqrt ( sin ( a / 2 ) * sin ( a / 2 ) + cos ( radLat1 ) * cos ( radLat2 ) * sin ( b / 2 ) * sin ( b / 2 ) ) ) * 6378 . 137 ;
double dis = 2 * asin ( sqrt ( sin ( a / 2 ) * sin ( a / 2 ) + cos ( radLat1 ) * cos ( radLat2 ) * sin ( b / 2 ) * sin ( b / 2 ) ) ) * 6378 . 137 ;
BigDecimal bigDecimalValue = new BigDecimal ( dis ) ;
bigDecimalValue = bigDecimalValue . setScale ( 3 , RoundingMode . DOWN ) ;
return bigDecimalValue ;
}
/**
@@ -54,28 +59,32 @@ public class LocationUtils {
*/
public static Map < String , double [ ] > returnLLSquarePoint ( double longitude , double latitude , double distanceInKm ) {
Map < String , double [ ] > squareMap = new HashMap < > ( ) ;
BigDecimal bdlongitude = new BigDecimal ( longitude ) ;
// 地球平均半径,单位:千米
double earthRadius = 6378 . 137 ;
BigDecimal earthRadius = new BigDecimal ( " 6378.137 " ) ;
// 将距离转换为弧度
double radialDistance = distanceInKm / earthRadius ;
BigDecimal radialDistance = BigDecimal . valueOf ( distanceInKm ) . divide ( earthRadius , 10 , RoundingMode . HALF_UP ) ;
// 计算纬度上变化对应的角度
double dLatitude = Math . toDegrees ( 2 * Math . asin ( Math . sin ( radialDistance / 2 ) / Math . cos ( Math . toRadians ( latitude ) ) ) ) ;
BigDecimal dLatitude = BigDecimal . valueOf ( Math . toDegrees ( 2 * Math . asin ( Math . sin ( radialDistance . divide ( BigDecimal . valueOf ( 2 ) ) . doubleValue ( ) ) / Math . cos ( Math . toRadians ( latitude ) ) ) ) ) ;
// 计算经度上变化对应的角度,这里需要考虑纬度对距离的影响
// 使用Haversine公式来估算在给定纬度上, 距离对应的经度变化
double estimatedLongitudeDistance = getDistanceFrom2LngLat ( latitude , longitude , latitude , longitude + 0 . 01 ) ; // 假设0.01度经度变化对应的距离
double dLongitude = distanceInKm / estimatedLongitudeDistance * 0 . 0192736 ; // 根据比例计算经度变化
BigDecimal estimatedLongitudeDistance = getDistanceFrom2LngLat ( latitude , longitude , latitude , bd longitude. add ( BigDecimal . valueOf ( 0 . 01 ) ) . doubleValue ( ) ) ; // 假设0.01度经度变化对应的距离
BigDecimal dLongitude = BigDecimal . valueOf ( distanceInKm ) . divide ( estimatedLongitudeDistance , 10 , RoundingMode . HALF_UP ) . multiply ( new BigDecimal ( " 0.0192736 " ) ) ; // 根据比例计算经度变化
// 正方形四个顶点的坐标
double [ ] rightTopPoint = { latitude + dLatitude / 2 , longitude + dLongitude / 2 } ;
double [ ] leftBottomPoint = { latitude - dLatitude / 2 , longitude - dLongitude / 2 } ;
double [ ] rightTopPoint = { BigDecimal . valueOf ( latitude ) . add ( dLatitude . divide ( BigDecimal . valueOf ( 2 ) ) ) . doubleValue ( ) , BigDecimal . valueOf ( longitude ) . add ( dLongitude . divide ( BigDecimal . valueOf ( 2 ) ) ) . doubleValue ( ) } ;
double [ ] leftBottomPoint = { BigDecimal . valueOf ( latitude ) . subtract ( dLatitude . divide ( BigDecimal . valueOf ( 2 ) ) ) . doubleValue ( ) , BigDecimal . valueOf ( longitude ) . subtract ( dLongitude . divide ( BigDecimal . valueOf ( 2 ) ) ) . doubleValue ( ) } ;
squareMap . put ( " rightTopPoint " , rightTopPoint ) ;
squareMap . put ( " leftBottomPoint " , leftBottomPoint ) ;
// 打印结果 rightTopPoint[0]纬度lng, rightTopPoint[1]经度lat
System. out . println ( " rightTop: " + rightTopPoint [ 0 ] + " ====== " + rightTopPoint [ 1 ] ) ;
System . out . println ( " leftBottom: " + leftBottomPoint [ 0 ] + " ====== " + leftBottomPoint [ 1 ] ) ;
// System.out.println("rightTop: " + rightTopPoint[0] + "======" + rightTopPoint[1]);
// System.out.println("leftBottom: " + leftBottomPoint[0] + "======" + leftBottomPoint[1]) ;
return squareMap ;
}
/**
* 将角度转化为弧度
*/
@@ -84,23 +93,20 @@ public class LocationUtils {
}
//1KM
public static void main ( String [ ] args ) {
Map < String , double [ ] > stringMap = returnLLSquarePoint ( 108 . 95439 8 , 34 . 308687 , 1 ) ;
Map < String , double [ ] > stringMap = returnLLSquarePoint ( 108 . 97 541 8 , 34 . 280890 , 5 ) ;
double [ ] leftTopPoints = stringMap . get ( " rightTopPoint " ) ;
double [ ] leftBottomPoints = stringMap . get ( " leftBottomPoint " ) ;
double lat2 = 108 . 975418 ;
double lon2 = 34 . 280890 ;
double distance3 = getDistanceFrom2LngLat ( 109 . 019993 , 34 . 342849 , lat2 , lon2 ) ;
BigDecimal distance3 = getDistanceFrom2LngLat ( 108 . 975418 , 34 . 280890 , 109 . 019993 , 34 . 342849 ) ;
System . out . println ( distance3 ) ;
// 计算距离
double distance1 = getDistanceFrom2LngLat ( leftTopPoints [ 1 ] , leftTopPoints [ 0 ] , lat2 , lon2 ) ;
double distance2 = getDistanceFrom2LngLat ( leftBottomPoints [ 1 ] , leftBottomPoints [ 0 ] , lat2 , lon2 ) ;
BigDecimal distance1 = getDistanceFrom2LngLat ( leftTopPoints [ 1 ] , leftTopPoints [ 0 ] , lat2 , lon2 ) ;
BigDecimal distance2 = getDistanceFrom2LngLat ( leftBottomPoints [ 1 ] , leftBottomPoints [ 0 ] , lat2 , lon2 ) ;
System . out . println ( " Distance between the two points is: " + distance1 + " km " ) ;
System . out . println ( " Distance between the two points is: " + distance2 + " km " ) ;
}
// public static void main(String[] args) {
// Map<String, double[]> stringMap = returnLLSquarePoint(34.342849, 109.019993, 1);
//
// }
//108.88883399281181(Double), 109.06200200718818(Double), 34.22653139523867(Double), 34.335248604761325(Double)
}