基于位置的时区检索

给定:LDAP存储用户的位置。

如何使用他们的位置驾驶他们的时区? 接受任何指针,首选Java语言。

提前致谢。

这取决于“位置”包含的信息? 您需要将位置映射到时区名称,最好是Olson样式时区名称,因为它们更详细,更容易映射,因为它们本身就是位置。

如果它是一个近似地址(如国家和城市等),那么几个地理定位服务确实在其信息中包含时区,因此您可以调用这些服务并查看。

如果它是具有纬度和经度的地理位置,那么名为Earthtools的站点可以为您提供时区。 http://www.earthtools.org/webservices.htm#timezone

这个数据库提供了从城市和国家到时区的映射: http : //citytimezones.info/cms/pending_requests.htm

不幸的是,它使用Windows时区名称,但您可以使用Unicode.org中的数据http://unicode.org/repos/cldr/trunk/common/supplemental/windowsZones.xml来映射Windows时区名称和Olson TZ名称。

我实际上没有这样做,但以下应该工作:

  1. 您可以先使用GeoGoogle java库获取来自城邦国家/地区的经度/纬度。

  2. 接下来,您可以使用Lennart提到的EarthTools (以及您自己的一些Java代码)来获取时区:)

我们使用MaxMind GeoIP数据库来获取有关用户位置的信息。 他们有付费版本(准确率99.8%)和免费版本 (准确率99.5%)。

它们还为您提供Java,C,PHP等API,使您可以查询其可以下载并保存在本地的数据库(每月提供更新)。 数据库根据IP地址为您提供有关客户城市,州,国家等的信息。

希望这可以帮助。

Try this code for use Google Time Zone API from Java: 
 String get_xml_server_reponse(String server_url){ URL xml_server = null; String xmltext = ""; InputStream input; try { xml_server = new URL(server_url); try { input = xml_server.openConnection().getInputStream(); final BufferedReader reader = new BufferedReader(new InputStreamReader(input)); final StringBuilder sBuf = new StringBuilder(); String line = null; try { while ((line = reader.readLine()) != null) { sBuf.append(line); } } catch (IOException e) { Log.e(e.getMessage(), "XML parser, stream2string 1"); } finally { try { input.close(); } catch (IOException e) { Log.e(e.getMessage(), "XML parser, stream2string 2"); } } xmltext = sBuf.toString(); } catch (IOException e1) { e1.printStackTrace(); } } catch (MalformedURLException e1) { e1.printStackTrace(); } return xmltext; } private String get_UTC_Datetime_from_timestamp(long timeStamp){ try{ Calendar cal = Calendar.getInstance(); TimeZone tz = cal.getTimeZone(); int tzt = tz.getOffset(System.currentTimeMillis()); timeStamp -= tzt; // DateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss",Locale.getDefault()); DateFormat sdf = new SimpleDateFormat(); Date netDate = (new Date(timeStamp)); return sdf.format(netDate); } catch(Exception ex){ return ""; } } class NTP_UTC_Time { private static final String TAG = "SntpClient"; private static final int RECEIVE_TIME_OFFSET = 32; private static final int TRANSMIT_TIME_OFFSET = 40; private static final int NTP_PACKET_SIZE = 48; private static final int NTP_PORT = 123; private static final int NTP_MODE_CLIENT = 3; private static final int NTP_VERSION = 3; // Number of seconds between Jan 1, 1900 and Jan 1, 1970 // 70 years plus 17 leap days private static final long OFFSET_1900_TO_1970 = ((365L * 70L) + 17L) * 24L * 60L * 60L; private long mNtpTime; public boolean requestTime(String host, int timeout) { try { DatagramSocket socket = new DatagramSocket(); socket.setSoTimeout(timeout); InetAddress address = InetAddress.getByName(host); byte[] buffer = new byte[NTP_PACKET_SIZE]; DatagramPacket request = new DatagramPacket(buffer, buffer.length, address, NTP_PORT); buffer[0] = NTP_MODE_CLIENT | (NTP_VERSION << 3); writeTimeStamp(buffer, TRANSMIT_TIME_OFFSET); socket.send(request); // read the response DatagramPacket response = new DatagramPacket(buffer, buffer.length); socket.receive(response); socket.close(); mNtpTime = readTimeStamp(buffer, RECEIVE_TIME_OFFSET); } catch (Exception e) { // if (Config.LOGD) Log.d(TAG, "request time failed: " + e); return false; } return true; } public long getNtpTime() { return mNtpTime; } /** * Reads an unsigned 32 bit big endian number from the given offset in the buffer. */ private long read32(byte[] buffer, int offset) { byte b0 = buffer[offset]; byte b1 = buffer[offset+1]; byte b2 = buffer[offset+2]; byte b3 = buffer[offset+3]; // convert signed bytes to unsigned values int i0 = ((b0 & 0x80) == 0x80 ? (b0 & 0x7F) + 0x80 : b0); int i1 = ((b1 & 0x80) == 0x80 ? (b1 & 0x7F) + 0x80 : b1); int i2 = ((b2 & 0x80) == 0x80 ? (b2 & 0x7F) + 0x80 : b2); int i3 = ((b3 & 0x80) == 0x80 ? (b3 & 0x7F) + 0x80 : b3); return ((long)i0 << 24) + ((long)i1 << 16) + ((long)i2 << 8) + (long)i3; } /** * Reads the NTP time stamp at the given offset in the buffer and returns * it as a system time (milliseconds since January 1, 1970). */ private long readTimeStamp(byte[] buffer, int offset) { long seconds = read32(buffer, offset); long fraction = read32(buffer, offset + 4); return ((seconds - OFFSET_1900_TO_1970) * 1000) + ((fraction * 1000L) / 0x100000000L); } /** * Writes 0 as NTP starttime stamp in the buffer. --> Then NTP returns Time OFFSET since 1900 */ private void writeTimeStamp(byte[] buffer, int offset) { int ofs = offset++; for (int i=ofs;i<(ofs+8);i++) buffer[i] = (byte)(0); } } String get_time_zone_time(GeoPoint gp){ String erg = ""; String raw_offset = ""; String dst_offset = ""; double Longitude = gp.getLongitudeE6()/1E6; double Latitude = gp.getLatitudeE6()/1E6; // String request = "http://ws.geonames.org/timezone?lat="+Latitude+"&lng="+ Longitude+ "&style=full"; long tsLong = 0; // System.currentTimeMillis()/1000; NTP_UTC_Time client = new NTP_UTC_Time(); if (client.requestTime("pool.ntp.org", 2000)) { tsLong = client.getNtpTime(); } if (tsLong != 0) { tsLong = tsLong / 1000; // https://maps.googleapis.com/maps/api/timezone/xml?location=39.6034810,-119.6822510&timestamp=1331161200&sensor=true String request = "https://maps.googleapis.com/maps/api/timezone/xml?location="+Latitude+","+ Longitude+ "&timestamp="+tsLong +"&sensor=true"; String xmltext = get_xml_server_reponse(request); if(xmltext.compareTo("")!= 0) { int startpos = xmltext.indexOf(" 

并使用它:

 GeoPoint gp = new GeoPoint(39.6034810,-119.6822510); String Current_TimeZone_Time = get_time_zone_time(gp);