从googleEarh导出的kml文件
<?xml version="1.0" encoding="UTF-8"?>
<kml xmlns="http://www.opengis.net/kml/2.2" xmlns:gx="http://www.google.com/kml/ext/2.2"><Document> <!-- Begin Style Definitions --> <Style id="line1"> <LineStyle> <color>FF808080</color> <width>1</width> </LineStyle> </Style> <Folder> <name>Line Features</name> <description>Line Features</description> <Placemark> <description>Unclassified Line Feature</description> <styleUrl>#line1</styleUrl> <LineString> <coordinates> 115.9676728167,40.4840735806,0 115.9537842111,40.4823857889,0 115.9563131444,40.4703987611,0 115.9551753833,40.4662973972,0 115.9554458000,40.4636396361,0 115.9397187972,40.4622803889,0 115.9405904556,40.4562066889,0 115.9408371611,40.4549313694,0 115.9422346222,40.4538901583,0 115.9448324639,40.4514630028,0 115.9574561306,40.4524817889,0 115.9619367944,40.4513946639,0 </coordinates> </LineString> </Placemark> </Folder></Document></kml>做工程中遇到需要解析kml文件并提取其中的经纬度坐标信息的需求,从网上查了一圈资料发现都不好用,干脆自己写,用正则表达式regex和split()方法实现了坐标信息提取功能。
主要遇到的问题是coordinates中的InnerText文本中有\t \n \r \f 或多空格问题,需要将这些因素排除。
\f 匹配一个换页符
\n 匹配一个换行符\r 匹配一个回车符\t 匹配一个制表符这些符号用正则表达式字符替换方式直接清除
Regex reg = new Regex("\f|\n|\r|\t");
string modified = reg.Replace(tt, "");多空格问题用split的StringSplitOptions.RemoveEmptyEntries来清除
string[] ss = modified.Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);//清除空格
这样就能得到纯粹的x,y,z字符串数组了.OK。
***********************************************************************************************************************************************
想了2种思路,目前第1种思路已经测试通过了,第2种思路懒得写了,哪位如果有兴趣实现了的话告诉我一声喔,,也算是饮水思源啦。
************************************************************************************************************************************************
代码如下:
private void KMLFileLoadButton_Click(object sender, EventArgs e)
{// 读取googleEarth的导出的kml/kmz路径文件 OpenFileDialog dlg = new OpenFileDialog(); dlg.Filter = "KML文件(*.kml)|*.kml|所有文件|*.*"; if (dlg.ShowDialog() != DialogResult.OK) return; string destPath = dlg.FileName;//CopyToRelavitePath(dlg.FileName); if (destPath == null) return; XmlDocument xmldoc = new XmlDocument(); xmldoc.Load(destPath); XmlElement root = xmldoc.DocumentElement; /规范命名空间 XmlNode _document = root.GetElementsByTagName("Document")[0]; XmlNamespaceManager nsmgr = new XmlNamespaceManager(xmldoc.NameTable); if (_document== null || _document.Attributes["xmlns"]==null) { nsmgr.AddNamespace("ns", root.Attributes["xmlns"].Value); } else { nsmgr.AddNamespace("ns", _document.Attributes["xmlns"].Value); } NGlbLine geo = new NGlbLine(3, false); XmlNodeList xmlmark = root.GetElementsByTagName("Placemark"); for (int m = 0; m < xmlmark.Count; m++) { XmlNodeList xmlmarkChilds = xmlmark[m].ChildNodes; for (int n = 0; n < xmlmarkChilds.Count; n++) { XmlNode node = xmlmarkChilds[n]; if (node.Name == "LineString" || node.Name == "LineRing") { XmlNode coordsNode = node.FirstChild; while (coordsNode != null && coordsNode.Name != "coordinates") { coordsNode = coordsNode.NextSibling; } if (coordsNode == null) continue; // 思路1 :用正则表达式去除字符串首位的制表符、换行符等符号,然后用' '来划分为string[] string tt = coordsNode.InnerText; Regex reg = new Regex("\f|\n|\r|\t"); string modified = reg.Replace(tt, ""); string[] ss = modified.Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);//清除空格 for (int cc = 0; cc < ss.Length; cc++) { string[] aa = ss[cc].Split(','); if (aa.Length == 3) geo.AddPoint(Convert.ToDouble(aa[0]), Convert.ToDouble(aa[1]), Convert.ToDouble(aa[2])); else if (aa.Length == 2) geo.AddPoint(Convert.ToDouble(aa[0]), Convert.ToDouble(aa[1]), 0); } // 思路2 :用regex正则表达式匹配 类似 115.9676728167,40.4840735806,0的样式字段 } } }.............................................
}