Winform实现用多线程、百度地图API解析某公司的物理地址
2015-12-01 21:47
489 查看
前言
作为一个很挫的C#新手总喜欢自己写点儿不着边际的东西,本人是个新手加菜鸟,写B/S的,工作中,任务完成了,空闲下来,总想继续学点儿什么,由此触发了本篇文章了。个人一直认为,.NET中,C/S所要求的技术含量要高得多,需要的知识也多得多。所以想多多研究研究。菜鸟文章!
![](http://images.cnitblog.com/i/624228/201408/150930441701359.png)
这是软件总图,很简单,就几个按钮。。。
![](http://images.cnitblog.com/i/624228/201408/150935276705170.jpg)
这里编写了一个批量导入Excel文件的功能,导入的Excel表内容如下:
![](http://images.cnitblog.com/i/624228/201408/150935542641761.png)
![](http://images.cnitblog.com/i/624228/201408/150935393275962.png)
导入Excel后,点击解析,解析出该公司的地理位置、经纬度、精确度、附近地标 and so on~~
![](http://images.cnitblog.com/i/624228/201408/150935455451997.png)
解析完成后,支持将结果导出到Excel文件,导出的结果如下图:
![](http://images.cnitblog.com/i/624228/201408/150936033425567.png)
主要是学习百度地图API、多线程的,所以没有精心设计皮肤,很朴素啦~~~
接下来说说是如何实现的,其实原理很简单(我也不会难的。囧。),先调用百度API接口(正向解析),将公司名发送过去,然后会返回一段Json,里面包含了该地址的经纬度,然后继续调用API(逆向解析),将经纬度发送过去,返回的Json中就包含了地理位置还有一系列其他内容,通过截取之类的操作就得到了我需要的内容。
多线程
当我完成百度地图部分后,我决定给自己的小软件加入批量解析功能,于是乎,出现了导入和导出Excel的功能,这个功能这里不多说,我的博客里面目前为止,基本上都是导入导出(继续 。囧囧。)。
当完成批量功能后,发现一执行解析,软件就假死状态,突然想起要用多线程。以前没用过多线程,继续百度一下,这方面的内容博客园里面挺多的。
经过上面的部分是启动多线程的代码,意外的发现,多线程其实很好弄。
不过,再次遇到问题,发现交给线程处理的方法,不能传递值进行,也就是需要进行线程资源共享,继续百度!
这里,我使用委托、创建类级变量共享资源,具体代码如下(不知道是否理解错了,若是有错误,希望能提点一二):
到这里,测试,OK!
UI线程和执行方法的线程分离了,软件UI不会在执行解析方法的时候假死了!
网络爬虫的资料网上不是很多,大部分都是自己琢磨的,某些地方肯定会存在问题,软件我也写的差不多了,确实能够找到公司的具体地理位置,但是还是存在许多问题的。
先贴一张图,以后有时间完善了,发篇博文上来!
![](http://images.cnitblog.com/i/624228/201408/151016369364577.png)
相关资料:
百度地图Geocoding API v2.0:http://developer.baidu.com/map/webservice-geocoding.htm
这里发上源代码(VS2010工程):http://download.csdn.net/detail/a406502972/7963037
作为一个很挫的C#新手总喜欢自己写点儿不着边际的东西,本人是个新手加菜鸟,写B/S的,工作中,任务完成了,空闲下来,总想继续学点儿什么,由此触发了本篇文章了。个人一直认为,.NET中,C/S所要求的技术含量要高得多,需要的知识也多得多。所以想多多研究研究。菜鸟文章!
环境
.NET3.5 + VS2010 + Geocoding API v2.0 +httpwebrequest/httpwebresponse软件截图
![](http://images.cnitblog.com/i/624228/201408/150930441701359.png)
这是软件总图,很简单,就几个按钮。。。
![](http://images.cnitblog.com/i/624228/201408/150935276705170.jpg)
这里编写了一个批量导入Excel文件的功能,导入的Excel表内容如下:
![](http://images.cnitblog.com/i/624228/201408/150935542641761.png)
![](http://images.cnitblog.com/i/624228/201408/150935393275962.png)
导入Excel后,点击解析,解析出该公司的地理位置、经纬度、精确度、附近地标 and so on~~
![](http://images.cnitblog.com/i/624228/201408/150935455451997.png)
解析完成后,支持将结果导出到Excel文件,导出的结果如下图:
![](http://images.cnitblog.com/i/624228/201408/150936033425567.png)
主要是学习百度地图API、多线程的,所以没有精心设计皮肤,很朴素啦~~~
代码部分
百度地图API接下来说说是如何实现的,其实原理很简单(我也不会难的。囧。),先调用百度API接口(正向解析),将公司名发送过去,然后会返回一段Json,里面包含了该地址的经纬度,然后继续调用API(逆向解析),将经纬度发送过去,返回的Json中就包含了地理位置还有一系列其他内容,通过截取之类的操作就得到了我需要的内容。
/// <summary> /// 地址逆向解析 /// </summary> /// <param name="AddressName"></param> public DataRow FindAddress(string AddressName, int i, DataRow dr) { try { string retString = HttpPost(string.Format("http://api.map.baidu.com/geocoder/v2/?ak=秘钥&callback=renderOption&output=json&address={0}&city=北京市&precise=1", AddressName)); retString = retString.Remove(0, 27).TrimEnd(')') + "\r\n"; string[] strs1 = retString.Split('{'); string[] strs2 = strs1[3].Split(','); string str3 = strs2[0].Split(':')[1]; string str4 = strs2[1].Split(':')[1].TrimEnd('}'); string str5 = strs2[3].Split(':')[1]; this.t_returnString.AppendText("经度:" + str3 + "\r\n" + "纬度:" + str4 + "\r\n" + "精确度:" + str5 + "\r\n"); string retLocad = HttpPost(string.Format("http://api.map.baidu.com/geocoder/v2/?ak=秘钥&callback=renderReverse&location={0}&output=json&pois=0", str4 + "," + str3)); //this.t_returnString.AppendText(retLocad + "\r\n"); string[] strs1_1 = retLocad.Split('{'); string[] strs2_1 = strs1_1[3].Split(','); string str3_1 = strs2_1[2].Split(':')[1]; string str4_1 = strs2_1[3].Split(':')[1] + "、" + strs2_1[4] + "、" + strs2_1[5]; this.t_returnString.AppendText("地理位置:" + str3_1 + "\r\n"); this.t_returnString.AppendText("附近地标:" + str4_1 + "\r\n"); this.t_returnString.ScrollToCaret();//滚动到光标处 dr["地理位置"] = str3_1; dr["附近地标"] = str4_1; dr["可信度"] = str5; } catch (Exception) { this.t_returnString.AppendText("暂无" + "\r\n"); } return dr; }
多线程
当我完成百度地图部分后,我决定给自己的小软件加入批量解析功能,于是乎,出现了导入和导出Excel的功能,这个功能这里不多说,我的博客里面目前为止,基本上都是导入导出(继续 。囧囧。)。
当完成批量功能后,发现一执行解析,软件就假死状态,突然想起要用多线程。以前没用过多线程,继续百度一下,这方面的内容博客园里面挺多的。
private void b_toExcel_Click(object sender, EventArgs e) { this.t_txtInfo.Enabled = false; this.button1.Enabled = false; this.b_openexcel.Enabled = false; this.b_toExcel.Enabled = false; WhileDataTable = ToDataTable(this.tb_url.Text, 0, true); //多线程启动 ThreadStart startDownload = new ThreadStart(WhileFunc); Thread downloadThread = new Thread(startDownload); //实例化要开启的新类 downloadThread.IsBackground = true; downloadThread.Start();//开启线程 }
经过上面的部分是启动多线程的代码,意外的发现,多线程其实很好弄。
不过,再次遇到问题,发现交给线程处理的方法,不能传递值进行,也就是需要进行线程资源共享,继续百度!
这里,我使用委托、创建类级变量共享资源,具体代码如下(不知道是否理解错了,若是有错误,希望能提点一二):
private delegate void DoDataDelegate(); //创建委托 private DataTable WhileDataTable = null; //全局变量 private DataTable ReturnTable = null; public void WhileFunc() { if (progressBar1.InvokeRequired) { DoDataDelegate d = WhileFunc; progressBar1.Invoke(d, null); } else { ReturnTable = new DataTable(); ReturnTable.Columns.Add("公司名", typeof(string)); ReturnTable.Columns.Add("可信度", typeof(string)); ReturnTable.Columns.Add("地理位置", typeof(string)); ReturnTable.Columns.Add("附近地标", typeof(string)); progressBar1.Maximum = (int)WhileDataTable.Rows.Count; for (int i = 0; i < (int)WhileDataTable.Rows.Count; i++) { DataRow row = ReturnTable.NewRow(); progressBar1.Value = i + 1; row["公司名"] = WhileDataTable.Rows[i][0]; this.t_returnString.AppendText("\r\n" + WhileDataTable.Rows[i][0] + ":\r\n"); row = FindAddress(WhileDataTable.Rows[i][0].ToString(), i, row); Application.DoEvents(); ReturnTable.Rows.Add(row); if (progressBar1.Value == progressBar1.Maximum) { this.Enabled = true; if (MessageBox.Show("数据解析完成,是否生成Excel文档?", "消息", MessageBoxButtons.OKCancel, MessageBoxIcon.Question, MessageBoxDefaultButton.Button2) == DialogResult.OK) { CreateSheet("地址解析结果", ReturnTable); } } } } }
到这里,测试,OK!
UI线程和执行方法的线程分离了,软件UI不会在执行解析方法的时候假死了!
后记
其实,这个软件有很大问题的,百度的API并不能准确的返回查询的公司信息,百度也不可能将所有的公司信息加载到他们的数据库里面去的。所以精确度有限,实用性差,练手吧!不过,在这个软件的启发下,我萌生了继续开发的想法,这次索性换了一种方法,决定用爬虫技术+多线程去爬行百度检索出来的网站,再通过网站内容检索、跳转找到这些公司的主页、或者相关页面,进一步得到该公司的准确地址信息!网络爬虫的资料网上不是很多,大部分都是自己琢磨的,某些地方肯定会存在问题,软件我也写的差不多了,确实能够找到公司的具体地理位置,但是还是存在许多问题的。
先贴一张图,以后有时间完善了,发篇博文上来!
![](http://images.cnitblog.com/i/624228/201408/151016369364577.png)
相关资料:
百度地图Geocoding API v2.0:http://developer.baidu.com/map/webservice-geocoding.htm
这里发上源代码(VS2010工程):http://download.csdn.net/detail/a406502972/7963037
相关文章推荐
- Oracle在存储过程中如何返回结果集
- NPOI导出Excel - 自动适应中文宽度(帮助类下载)
- C# 使用 NPOI 库读写 Excel 文件(转载)
- ADO.NET 读取Excel文件,并作数据源
- 多种时间验证方法
- 水晶报表初体验(Visual Studio 2010)
- linux命令编辑技巧
- Asp.net导出Excel续章(自定义合并单元格,非Office组件)
- 【数据传输 1】服务器—>客户端之间的数据类型转换
- Asp.net中导出Excel文档(Gridview)
- Asp.net导出Excel(HTML输出方法)
- #ifdef,#if等条件编译
- mvc小技巧
- Asp.net通过模板(.dot/Html)导出Word,同时导出图片
- 取两个DataTable的交集,删除重复数据
- 简单了解委托、泛型委托、表达式树、Lambda等
- studio使用技巧
- Oracle DBA常用的几条命令
- Oracle的导入导出
- Oracle建立表空间和用户