從googleEarh導出的kml文件node
<?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>c++
作工程中遇到須要解析kml文件並提取其中的經緯度座標信息的需求,從網上查了一圈資料發現都很差用,乾脆本身寫,用正則表達式regex和split()方法實現了座標信息提取功能。正則表達式
主要遇到的問題是coordinates中的InnerText文本中有\t \n \r \f 或多空格問題,須要將這些因素排除。數組
\f 匹配一個換頁符
\n 匹配一個換行符
\r 匹配一個回車符
\t 匹配一個製表符測試
這些符號用正則表達式字符替換方式直接清除google
Regex reg = new Regex("\f|\n|\r|\t");
string modified = reg.Replace(tt, "");spa
多空格問題用split的StringSplitOptions.RemoveEmptyEntries來清除.net
string[] ss = modified.Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);//清除空格xml
這樣就能獲得純粹的x,y,z字符串數組了.OK。ip
***********************************************************************************************************************************************
想了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的樣式字段
}
}
}
............................................. }