From 854b917a9bfc0905a33992e00bec78e3882047c4 Mon Sep 17 00:00:00 2001 From: lixiangrong Date: Thu, 17 Mar 2016 10:34:49 +0800 Subject: [PATCH] =?UTF-8?q?GeoHash=E7=AE=97=E6=B3=95=20AES=E5=8A=A0?= =?UTF-8?q?=E5=AF=86=E7=AE=97=E6=B3=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/osc/git/eh3/test/TestCode.java | 42 +++--- .../java/osc/git/eh3/test/TestGeoHash.java | 29 ++++ .../java/osc/git/eh3/utils/AESEncrypter.java | 135 ++++++++++++++++++ .../java/osc/git/eh3/utils/CommonUtils.java | 65 +++++++++ src/main/java/osc/git/eh3/utils/GeoHash.java | 116 +++++++++++++++ src/main/resources/generatorConfig.xml | 3 +- 6 files changed, 372 insertions(+), 18 deletions(-) create mode 100644 src/main/java/osc/git/eh3/test/TestGeoHash.java create mode 100644 src/main/java/osc/git/eh3/utils/AESEncrypter.java create mode 100644 src/main/java/osc/git/eh3/utils/GeoHash.java diff --git a/src/main/java/osc/git/eh3/test/TestCode.java b/src/main/java/osc/git/eh3/test/TestCode.java index ad5f09c..adcb38f 100644 --- a/src/main/java/osc/git/eh3/test/TestCode.java +++ b/src/main/java/osc/git/eh3/test/TestCode.java @@ -1,24 +1,13 @@ package osc.git.eh3.test; -import java.lang.annotation.Annotation; -import java.lang.reflect.Method; -import java.math.BigDecimal; -import java.net.InetAddress; -import java.net.UnknownHostException; import java.text.ParseException; import java.text.SimpleDateFormat; import java.util.Arrays; -import java.util.Calendar; import java.util.Date; import java.util.HashSet; import java.util.Set; -import com.caucho.hessian.client.HessianProxyFactory; - -import net.sf.ezmorph.bean.MorphDynaBean; -import net.sf.json.JSONArray; -import net.sf.json.JSONObject; -import osc.git.eh3.readlogs.IReadLogs; +import osc.git.eh3.utils.AESEncrypter; public class TestCode { @@ -167,11 +156,30 @@ public class TestCode { // SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss.SSS"); // System.out.println(sdf.format(dd)); - JSONObject groupAdxs = JSONObject.fromObject("{\"4ebdb328-5d4b-42e6-80c3-a6aaaecdcea1\":[\"1e03319c-425d-4a17-a6bf-eeec2f48db29\",\"1fed4171-9925-4834-aa7b-9b4d3a58841b\",\"ce579246-e707-4cb9-b982-88cad7944b92\"],\"9262cbe8-a9dc-4f4e-888b-cf3ffe65defd\":\"ce579246-e707-4cb9-b982-88cad7944b92\"}"); - Set keySet = groupAdxs.keySet(); - for (Object object : keySet) { - System.out.println(groupAdxs.get(object).getClass().isArray()); - } +// JSONObject groupAdxs = JSONObject.fromObject("{\"4ebdb328-5d4b-42e6-80c3-a6aaaecdcea1\":[\"1e03319c-425d-4a17-a6bf-eeec2f48db29\",\"1fed4171-9925-4834-aa7b-9b4d3a58841b\",\"ce579246-e707-4cb9-b982-88cad7944b92\"],\"9262cbe8-a9dc-4f4e-888b-cf3ffe65defd\":\"ce579246-e707-4cb9-b982-88cad7944b92\"}"); +// Set keySet = groupAdxs.keySet(); +// for (Object object : keySet) { +// System.out.println(groupAdxs.get(object).getClass().isArray()); +// } + +// System.out.println(UUID.randomUUID().toString()); + +// System.out.println(new Integer(0x11)); +// System.out.println(Integer.toBinaryString(30000)); +// System.out.println(Integer.valueOf("11", 16)); +// System.out.println(Integer.valueOf("11", 2)); + + + System.out.println(AESEncrypter.encrypt("lixiangrong")); + System.out.println(AESEncrypter.decrypt(AESEncrypter.encrypt("lixiangrong"))); + + System.out.println(AESEncrypter.encrypt("lixiangrong","ca048b18cac58865a8")); + System.out.println(AESEncrypter.decrypt(AESEncrypter.encrypt("lixiangrong","ca048b18cac58865a8"),"ca048b18cac58865a8")); + +// byte[] bytes = "lixiangrong".getBytes(); +// for (int i = 0; i < bytes.length; i++) { +// System.out.println(bytes[i]); +// } } public static Long parseDate(String s) { diff --git a/src/main/java/osc/git/eh3/test/TestGeoHash.java b/src/main/java/osc/git/eh3/test/TestGeoHash.java new file mode 100644 index 0000000..adc68d5 --- /dev/null +++ b/src/main/java/osc/git/eh3/test/TestGeoHash.java @@ -0,0 +1,29 @@ +package osc.git.eh3.test; + +import osc.git.eh3.utils.CommonUtils; +import osc.git.eh3.utils.GeoHash; + +public class TestGeoHash { + + + public static void main(String[] args) { + double lon1 = 109.0145193757; + double lat1 = 34.236080797698; + double lon2 = 108.9644583556; + double lat2 = 34.286439088548; + double dist; + String geocode; + + dist = CommonUtils.getDistance(lon1, lat1, lon2, lat2); + System.out.println("两点相距:" + dist + " 米"); + + geocode = GeoHash.encode(lat1, lon1); + System.out.println("当前位置编码:" + geocode); + + geocode = GeoHash.encode(lat2, lon2); + System.out.println("远方位置编码:" + geocode); + + System.out.println(GeoHash.decode("s6q8mc6nbupd")[0]+" "+GeoHash.decode("s6q8mc6nbupd")[1]); + + } +} \ No newline at end of file diff --git a/src/main/java/osc/git/eh3/utils/AESEncrypter.java b/src/main/java/osc/git/eh3/utils/AESEncrypter.java new file mode 100644 index 0000000..dff1165 --- /dev/null +++ b/src/main/java/osc/git/eh3/utils/AESEncrypter.java @@ -0,0 +1,135 @@ +package osc.git.eh3.utils; + +import java.security.InvalidAlgorithmParameterException; +import java.security.InvalidKeyException; +import java.security.NoSuchAlgorithmException; +import java.security.SecureRandom; +import java.security.spec.AlgorithmParameterSpec; +import javax.crypto.BadPaddingException; +import javax.crypto.Cipher; +import javax.crypto.IllegalBlockSizeException; +import javax.crypto.KeyGenerator; +import javax.crypto.NoSuchPaddingException; +import javax.crypto.SecretKey; +import javax.crypto.spec.IvParameterSpec; + +public class AESEncrypter { + + private static byte[] iv = new byte[] { 21, 22, 50, 44, -16, 124, -40, -114, -11, -40, 37, 23, -33, 23, -33, 75 }; + private static String defalut_key = "defalut_keydefalut_key"; + + /** + * 加密 + * + * @param content + * 要加密的内容 + * @return 加密后的32位字符串 + */ + public static String encrypt(String content) { + return encrypt(content, defalut_key); + } + + /** + * 解密 + * + * @param content + * AES密文 + * @return 解密后的内容 + */ + public static String decrypt(String content) { + return decrypt(content, defalut_key); + } + + /** + * 加密 + * + * @param content + * 要加密的内容 + * @param key + * 秘钥 + * @return 加密后的32位字符串 + */ + public static String encrypt(String content, String key) { + String str = ""; + try { + KeyGenerator kgen = KeyGenerator.getInstance("AES"); + kgen.init(128, new SecureRandom(key.getBytes())); + AlgorithmParameterSpec paramSpec = new IvParameterSpec(iv); + SecretKey skey = kgen.generateKey(); + Cipher ecipher = Cipher.getInstance("AES/CBC/PKCS5Padding"); + ecipher.init(Cipher.ENCRYPT_MODE, skey, paramSpec); + str = asHex(ecipher.doFinal(content.getBytes())); + } catch (BadPaddingException e) { + e.printStackTrace(); + } catch (NoSuchAlgorithmException e) { + e.printStackTrace(); + } catch (NoSuchPaddingException e) { + e.printStackTrace(); + } catch (InvalidKeyException e) { + e.printStackTrace(); + } catch (InvalidAlgorithmParameterException e) { + e.printStackTrace(); + } catch (IllegalBlockSizeException e) { + e.printStackTrace(); + } + return str; + } + + /** + * 解密 + * + * @param content + * AES密文 + * @param key + * 秘钥 + * @return 解密后的内容 + */ + public static String decrypt(String content, String key) { + try { + KeyGenerator kgen = KeyGenerator.getInstance("AES"); + kgen.init(128, new SecureRandom(key.getBytes())); + AlgorithmParameterSpec paramSpec = new IvParameterSpec(iv); + SecretKey skey = kgen.generateKey(); + Cipher dcipher = Cipher.getInstance("AES/CBC/PKCS5Padding"); + dcipher.init(Cipher.DECRYPT_MODE, skey, paramSpec); + return new String(dcipher.doFinal(asBin(content))); + } catch (BadPaddingException e) { + e.printStackTrace(); + } catch (NoSuchAlgorithmException e) { + e.printStackTrace(); + } catch (NoSuchPaddingException e) { + e.printStackTrace(); + } catch (InvalidKeyException e) { + e.printStackTrace(); + } catch (InvalidAlgorithmParameterException e) { + e.printStackTrace(); + } catch (IllegalBlockSizeException e) { + e.printStackTrace(); + } + return ""; + } + + private static String asHex(byte buf[]) { + StringBuffer strbuf = new StringBuffer(buf.length * 2); + int i; + for (i = 0; i < buf.length; i++) { + if (((int) buf[i] & 0xff) < 0x10) + strbuf.append("0"); + strbuf.append(Long.toString((int) buf[i] & 0xff, 16)); + } + return strbuf.toString(); + } + + private static byte[] asBin(String src) { + if (src.length() < 1) + return null; + byte[] encrypted = new byte[src.length() / 2]; + for (int i = 0; i < src.length() / 2; i++) { + int high = Integer.parseInt(src.substring(i * 2, i * 2 + 1), 16); + int low = Integer.parseInt(src.substring(i * 2 + 1, i * 2 + 2), 16); + + encrypted[i] = (byte) (high * 16 + low); + } + return encrypted; + } +} diff --git a/src/main/java/osc/git/eh3/utils/CommonUtils.java b/src/main/java/osc/git/eh3/utils/CommonUtils.java index 4fed7c7..844f11e 100644 --- a/src/main/java/osc/git/eh3/utils/CommonUtils.java +++ b/src/main/java/osc/git/eh3/utils/CommonUtils.java @@ -12,6 +12,18 @@ import java.util.Map; import javax.servlet.http.HttpServletRequest; public class CommonUtils { + private static double EARTH_RADIUS = 6371; // 默认地球半径(单位km) + + /** + * 转化为弧度(rad) + * + * @param d + * @return + */ + private static double rad(double d) { + return d * Math.PI / 180.0; + } + /** * 对象转换成另一个类对象 * @@ -149,4 +161,57 @@ public class CommonUtils { } return ipAddress; } + + /** + * 计算经纬度点对应正方形4个点的坐标 + * + * @param longitude + * @param latitude + * @param distance + * @return + */ + public static Map returnLLSquarePoint(double longitude, double latitude, double distance) { + Map squareMap = new HashMap(); + // 计算经度弧度,从弧度转换为角度 + double dLongitude = 2 * (Math.asin(Math.sin(distance / (2 * EARTH_RADIUS)) / Math.cos(Math.toRadians(latitude)))); + dLongitude = Math.toDegrees(dLongitude); + // 计算纬度角度 + double dLatitude = distance / EARTH_RADIUS; + dLatitude = Math.toDegrees(dLatitude); + // 正方形 + double[] leftTopPoint = { latitude + dLatitude, longitude - dLongitude }; + double[] rightTopPoint = { latitude + dLatitude, longitude + dLongitude }; + double[] leftBottomPoint = { latitude - dLatitude, longitude - dLongitude }; + double[] rightBottomPoint = { latitude - dLatitude, longitude + dLongitude }; + squareMap.put("leftTopPoint", leftTopPoint); + squareMap.put("rightTopPoint", rightTopPoint); + squareMap.put("leftBottomPoint", leftBottomPoint); + squareMap.put("rightBottomPoint", rightBottomPoint); + return squareMap; + } + + /** + * 基于googleMap中的算法得到两经纬度之间的距离,计算精度与谷歌地图的距离精度差不多,相差范围在0.2米以下 + * + * @param lon1 + * 第一点的精度 + * @param lat1 + * 第一点的纬度 + * @param lon2 + * 第二点的精度 + * @param lat3 + * 第二点的纬度 + * @return 返回的距离,单位m + */ + public static double getDistance(double lon1, double lat1, double lon2, double lat2) { + double radLat1 = rad(lat1); + double radLat2 = rad(lat2); + double a = radLat1 - radLat2; + double b = rad(lon1) - rad(lon2); + double s = 2 + * Math.asin(Math.sqrt(Math.pow(Math.sin(a / 2), 2) + Math.cos(radLat1) * Math.cos(radLat2) * Math.pow(Math.sin(b / 2), 2))); + s = s * EARTH_RADIUS * 1000; + s = Math.round(s * 10000) / 10000; + return s; + } } diff --git a/src/main/java/osc/git/eh3/utils/GeoHash.java b/src/main/java/osc/git/eh3/utils/GeoHash.java new file mode 100644 index 0000000..428ebbf --- /dev/null +++ b/src/main/java/osc/git/eh3/utils/GeoHash.java @@ -0,0 +1,116 @@ +package osc.git.eh3.utils; + +import java.util.BitSet; +import java.util.HashMap; + +/** + * GeoHash算法实现 + * + * @author lixiangrong + * + * 1、GeoHash将经纬度转换成一个可以排序,可以比较的字符串编码 + * 2、GeoHash表示的并不是一个点,而是一个矩形区域。比如编码wx4g0ec19,它表示的是一个矩形区域 + * + */ +public class GeoHash { + private static int numbits = 6 * 5; + final static char[] digits = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'j', 'k', 'm', 'n', + 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z' }; + + final static HashMap lookup = new HashMap(); + + static { + int i = 0; + for (char c : digits) + lookup.put(c, i++); + } + + public static double[] decode(String geohash) { + StringBuilder buffer = new StringBuilder(); + for (char c : geohash.toCharArray()) { + + int i = lookup.get(c) + 32; + buffer.append(Integer.toString(i, 2).substring(1)); + } + + BitSet lonset = new BitSet(); + BitSet latset = new BitSet(); + + // even bits + int j = 0; + for (int i = 0; i < numbits * 2; i += 2) { + boolean isSet = false; + if (i < buffer.length()) + isSet = buffer.charAt(i) == '1'; + lonset.set(j++, isSet); + } + + // odd bits + j = 0; + for (int i = 1; i < numbits * 2; i += 2) { + boolean isSet = false; + if (i < buffer.length()) + isSet = buffer.charAt(i) == '1'; + latset.set(j++, isSet); + } + // 中国地理坐标:东经73°至东经135°,北纬4°至北纬53° + double lon = decode(lonset, 70, 140); + double lat = decode(latset, 0, 60); + + return new double[] { lat, lon }; + } + + private static double decode(BitSet bs, double floor, double ceiling) { + double mid = 0; + for (int i = 0; i < bs.length(); i++) { + mid = (floor + ceiling) / 2; + if (bs.get(i)) + floor = mid; + else + ceiling = mid; + } + return mid; + } + + public static String encode(double lat, double lon) { + BitSet latbits = getBits(lat, 0, 60); + BitSet lonbits = getBits(lon, 70, 140); + StringBuilder buffer = new StringBuilder(); + for (int i = 0; i < numbits; i++) { + buffer.append((lonbits.get(i)) ? '1' : '0'); + buffer.append((latbits.get(i)) ? '1' : '0'); + } + return base32(Long.parseLong(buffer.toString(), 2)); + } + + private static BitSet getBits(double lat, double floor, double ceiling) { + BitSet buffer = new BitSet(numbits); + for (int i = 0; i < numbits; i++) { + double mid = (floor + ceiling) / 2; + if (lat >= mid) { + buffer.set(i); + floor = mid; + } else { + ceiling = mid; + } + } + return buffer; + } + + private static String base32(long i) { + char[] buf = new char[65]; + int charPos = 64; + boolean negative = (i < 0); + if (!negative) + i = -i; + while (i <= -32) { + buf[charPos--] = digits[(int) (-(i % 32))]; + i /= 32; + } + buf[charPos] = digits[(int) (-i)]; + + if (negative) + buf[--charPos] = '-'; + return new String(buf, charPos, (65 - charPos)); + } +} \ No newline at end of file diff --git a/src/main/resources/generatorConfig.xml b/src/main/resources/generatorConfig.xml index 92a4ab0..38027a2 100644 --- a/src/main/resources/generatorConfig.xml +++ b/src/main/resources/generatorConfig.xml @@ -25,7 +25,8 @@ -
+
+
\ No newline at end of file