博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
超简单方法实现省/市/地区级联查询
阅读量:6655 次
发布时间:2019-06-25

本文共 4484 字,大约阅读时间需要 14 分钟。

本文的原文连接是: 未经博主允许不得转载。

博主地址是:

1,关于中国地址

开发业务的时候遇到一个问题

需要弄一个省、市,地区的级联查询。
页面好做,但是数据不太好弄,不好组织。
开始考虑抓一个现成的数据库,存储成表机构,然后查询。
发现这个是一个效率比较低的方案,但维护起来比较好。
直接对数据库进行操作行了。

2,一个简单的方案

首先要招到数据源:

从中国统计局页面拷贝数据:
结果页面
将数据拷贝到一个district.data.dic文本里面。
邮政编码一共6位,1-2位代表省,3-4位代表市,5-6位代表区/县。
所以,可以直接将这个数据存储成一个3级树形结构。

3,代码实现

首先判断 1-2位,找到1级省。

然后找到3-4位,判断市,最后5-6位是区/县。

import com.google.common.base.Strings;import java.io.File;import java.nio.charset.Charset;import java.nio.file.Files;import java.util.HashMap;import java.util.List;import java.util.Map;public class DistrictUtils {    static class Tree {        private String code;        private String name;        private Map
children = new HashMap
(); public String getCode() { return code; } public void setCode(String code) { this.code = code; } public String getName() { return name; } public void setName(String name) { this.name = name; } public Map
getChildren() { return children; } public void addChildrenTree(String childrenCode, Tree childrenTree) { this.children.put(childrenCode, childrenTree); } } private static Map
addressTreeMap = new HashMap
(); static { try { // 取得运行时路径 String basePath = DistrictUtils.class.getResource("/") .toString().replace("file:", ""); System.out.println(basePath); List
lines = Files.readAllLines(new File(basePath + "district.data.dic").toPath(), Charset.forName("utf-8")); //循环数据。 for (String line : lines) { if (!Strings.isNullOrEmpty(line) && line.length() > 7) { String code = line.substring(0, 6); String name = line.substring(7); //里面包括了1种特殊的空格(\u3000特殊的中文空格!!!)。 name = name.replaceAll("\t", "").replaceAll("\\u3000", "").replaceAll(" ", ""); String codeTmp1 = code.substring(0, 2); String codeTmp2 = code.substring(2, 4); String codeTmp3 = code.substring(4, 6); //找到根节点。 if (codeTmp2.equals("00") && codeTmp3.equals("00")) { Tree baseTree = new Tree(); baseTree.setCode(code); baseTree.setName(name); addressTreeMap.put(code, baseTree); } else if (codeTmp3.equals("00")) { //找到二级节点 Tree secondTree = new Tree(); secondTree.setCode(code); secondTree.setName(name); //找到根节点,然后增加子树。 Tree baseTree = addressTreeMap.get(codeTmp1 + "0000"); if (baseTree != null) { baseTree.addChildrenTree(code, secondTree); } else { System.err.println("no tree " + codeTmp1 + "0000"); } } else { //剩下是3级节点。 Tree thirdTree = new Tree(); thirdTree.setCode(code); thirdTree.setName(name); //找到根节点。 Tree baseTree = addressTreeMap.get(codeTmp1 + "0000"); //然后找到二级节点,再增加子树。 Tree secondTree = baseTree.getChildren().get(codeTmp1 + codeTmp2 + "00"); if (secondTree != null) { secondTree.addChildrenTree(code, thirdTree); } else { System.err.println("no tree " + codeTmp1 + codeTmp2 + "00"); } } } } } catch (Exception e) { } } public static void loopTree(Tree addressTree, int level) { for (int i = 0; i < level; i++) { System.out.print("├─"); } System.out.printf("[%s][%s]\n", addressTree.getCode(), addressTree.getName()); int nextLevel = level + 1; for (Tree addressTreeTemp : addressTree.getChildren().values()) { loopTree(addressTreeTemp, nextLevel); } } public static void main(String[] args) { System.out.println(); System.out.println(); for (Tree addressTree : addressTreeMap.values()) { loopTree(addressTree, 1); } }}

运行结果:

├─[120000][天津市]├─├─[120100][市辖区]├─├─├─[120102][河东区]├─├─├─[120103][河西区]├─├─├─[120104][南开区]├─├─├─[120105][河北区]├─├─├─[120101][和平区]├─├─├─[120112][津南区]├─├─├─[120111][西青区]├─├─├─[120110][东丽区]├─├─├─[120116][滨海新区]├─├─├─[120106][红桥区]├─├─├─[120115][宝坻区]├─├─├─[120114][武清区]├─├─├─[120113][北辰区]├─├─[120200][县]├─├─├─[120225][蓟县]├─├─├─[120223][静海县]├─├─├─[120221][宁河县]├─[110000][北京市]├─├─[110200][县]├─├─├─[110229][延庆县]├─├─├─[110228][密云县]├─├─[110100][市辖区]├─├─├─[110114][昌平区]├─├─├─[110115][大兴区]├─├─├─[110116][怀柔区]├─├─├─[110117][平谷区]├─├─├─[110108][海淀区]├─├─├─[110111][房山区]├─├─├─[110107][石景山区]├─├─├─[110112][通州区]├─├─├─[110113][顺义区]├─├─├─[110109][门头沟区]├─├─├─[110106][丰台区]├─├─├─[110105][朝阳区]├─├─├─[110102][西城区]├─├─├─[110101][东城区]......

这里面有个坑,找了半天才发现,国家统计局里面使用了一个非常特殊的中文空格,咋进行字符串过滤都去不掉。

就是字符 \u3000 ,这个也是一个空字符串。直接晕死!!!
转码才发现的:

4,总结

本文的原文连接是: 未经博主允许不得转载。

博主地址是:

思路还是对的,中间遇到一个特殊空格的问题。

直接把这个树存储到内存,第一次加载使用,不用查询数据库了。
而且统计局这个数据更新的也比较慢,也就几年一次,够用了。
对于查询,同样的按照 1-2 , 3-4, 5-6 3级数据查询即可。

你可能感兴趣的文章
java-第八章-幸运抽奖-实现注册功能
查看>>
连接池和数据源
查看>>
httpd服务的简单配置
查看>>
系统管理员权限的用户过多
查看>>
Netty高性能之道
查看>>
我的友情链接
查看>>
iOS md5 32位加密(区分大小写)
查看>>
Linux 系统管理总结笔记
查看>>
JQuery学习笔记-JQuery常用插件
查看>>
接口实现单例模式
查看>>
华为S2300交换机基本配置
查看>>
手工设定ARP条目在Cisco路由器ARP列表中的保存时间
查看>>
Android Intent Flag的介绍
查看>>
使用O7_DICTIONARY_ACCESSIBILITY参数实现真正的“select any table”授权
查看>>
jquery 中 处理 json
查看>>
Qt实现自定义按钮的三态效果
查看>>
QStringList类常用方法
查看>>
5款让你的旧电脑重获新生的Linux发行版
查看>>
罗森伯格2012区域数据机房建设及运维高层论坛
查看>>
Linux下自动分割Nginx日志文件(三)-----Logrotate
查看>>