从CSV文件(融合表和KML的解决方法)提取数据 [英] Extracting data from CSV file (fusion table and kml workaround)

查看:586
本文介绍了从CSV文件(融合表和KML的解决方法)提取数据的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

像这样在此基础上在Xamarin Android版Google地图href=\"https://www.youtube.com/watch?v=WU1WbkEviMM\" rel=\"nofollow\">教程

 公共无效OnMapReady(GoogleMap的GoogleMap的)
{
MMAP = GoogleMap的;
的PolylineOptions几何=新的PolylineOptions()
。新增(新经纬度(37.35,-37.0123))
。新增(新经纬度(37.35,-37.0123))
。新增(新的经纬度(37.35,-37.0123));


折线折线= mMap.AddPolyline(几何)

}



不过,我已经从我的融合表层下载一个CSV文件从谷歌地图,因为我认为这可能是与多边形/折线数据,最简单的选项。输出看起来是这样的:

 描述,名称,标签,几何
,高地,61,<多边形> ;< outerBoundaryIs><线性环><&坐标GT; -5.657018,57.3352 -5.656396,57.334463 -5.655076,57.334556 -5.653439,57.334477 -5.652366,57.334724 -5.650064,57.334477 -5.648096,57.335082 -5.646846,57.335388 -5.644733,57.335539 ​​ - 5.643309,57.335428 -5.641981,57.335448 -5.640451,57.33578 -5.633217,57.339118 -5.627278,57.338921 -5.617161,57.337649 -5.607948,57.341015 -5.595812,57.343583 -5.586043,57.345373 -5.583581,57.350648 -5.576851,57.353609 -5.570088,57.354017 -5.560732, 57.354102 -5.555254,57.354033 -5.549713,57.353146 -5.547766,57.352275 -5.538932,57.352255 -5.525891,57.356217 -5.514888,57.361865 -5.504272,57.366027 -5.494515,57.374515 -5.469829,57.383765 -5.458661,57.389781 -5.453695,57.395033 -5.454057,57.402943 - 5.449189,57.40731 -5.440583,57.411447 -5.436133,57.414616 -5.438312,57.415474 -5.438628,57.417955 -5.440956,57.417909 -5.444013,57.414976 -5.450778,57.421362 -5.455035,57.422333 -5.462081,57.420719 -5.468775,57.416975 -5.475205,57.41135 -5.475976, 57.409117 -5.47705,57.407092 -5.478101,57.406056 -5.478901,57.40536 -5.479489,57.404534 -5.480051,57.403782 -5.481036,57.403107 -5.484538,57.402102 -5.485647,57.401856 -5.487358,57.401287 -5.488709,57.400962 -5.490175,57.400616 -5.491116,57.400176 - 5.493832,57.399318 -5.495279,57.399134 -5.496726,57.39771 -5.498724,57.396836 -5.49974,57.396314 -5.501317,57.39627 -5.502869,57.395426< /坐标>< /线性环>< / innerBoundaryIs>< /多边形>中
,斯特拉斯克莱德63,<&多边形GT;< outerBoundaryIs><线性环><&坐标GT; -5.603129,56.313564 -5.603163,56.312536 -5.603643,56.311794 -5.601467,56.311875 -5.601038,56.312481 -5.600697,56.313489 -5.60071,56.31535 -5.60159,56.316107 -5.600729,56.316598 -5.598625,56.3160​​58 -5.596203,56.317477 -5.597024,56.318119 -5.596095,56.318739 -5.595432,56.320116 -5.589343,56.322469 -5.584888,56.325178 -5.582907,56.327169 -5.581414,56.327472 -5.581435 ,56.326663 -5.582355,56.325602 -5.581515,56.323891 -5.576993,56.331062 -5.57886,56.331475 -5.57676,56.334449 -5.572748,56.335689 -5.569012,56.338143 -5.564802,56.342113 -5.555237,56.346668 -5.551214,56.347448 -5.547651,56.346391 -5.54444,56.344945 -5.541247,56.345945 -5.539099,56.349674 -5.533874,56.34763 -5.525195,56.342888 -5.523518,56.345066 -5.52345,56.346605 -5.526417,56.354361 -5.535455,56.353681 -5.537463,56.35508 -5.536035,56.356271 -5.538923,56.357205 -5.53891,56.359336 -5.539952 ,56.361491 -5.538102,56.36372 -5.535934,56.36567 -5.53392,56.367705 -5.531369,56.369729 -5.529853,56.371022 -5.532371,56.371274 -5.534177,56.371708 -5.532846,56.373256 -5.529845,56.37496 -5.527675,56.375327 -5.528531,56.375995 -5.526732,56.3763​​43 -5.525442,56.377809 -5.524739,56.379843 -5.526069,56.380561< /坐标>< /线性环>< / innerBoundaryIs>< /多边形>中



我上传了KML文件,以谷歌地图融合表层,它就创造了地图。然后我去文件>&下载GT; CSV 键,它给了我上面的例子。



我加入这个CSV文件到我的资产,我xamarin谷歌Android地图应用程序的文件夹,我的问题是,因为经纬度有两个双打作为其输入,是有办法,我可以输入从CSV文件中的上述数据代入这个方法,如果又如何?



不知道如何看了上面的CSV 然后提取<坐标> 然后添加这些坐标作为新的经纬度在上面的示例代码?



如果您发现然而坐标分成lat和液化天然气再下一经纬度是由空格分隔 -5.657018,57.3352 -5.656396,57.334463



须藤代码(这可能会或可能不会要求xamarin或Android体验,可能只需要C#/ LINQ)

 阅读CSV VAR SR =新的StreamReader(阅读从资产文件夹CSV);多边形> 
在包含双qoutes
Foreach源项目中删除Qoutes和< CSV
提取项目中删除描述,名称,标签,几何
Foreach源线474; outerBoundaryIs><线性环> ;<&坐标GT;从开始和结束
用空格分隔提取Foreach源项目协调
(现在,这将留下的37.35一长串,-37.0123坐标每行)在这样的事情也许
将?:

公共类行
{
公共双纬度{搞定;组; }
公共双LNG {搞定;组; }

公共行(字符串str)
{
的String [] =分隔符{,};
VAR ARR = str.Split(分隔符,StringSplitOptions.None);
纬度= Convert.ToDouble(ARR [0]);
LNG = Convert.ToDouble(ARR [1]);
}
}


私人无效OnMapReady()
无功行=新的List<行>();

名称Foreach源/新行
的PolylineOptions几何=新的PolylineOptions()
的ForEach(行项目)//不知道如何折线选项将采取的foreach
。加入(新经纬度(item.Lat,item.Lng))
折线折线= mMap.AddPolyline(几何)



由于没有在Xamarin的Andr​​oid与谷歌地图API V2,这可能提供了使用融合表图层的方式一个快速和容易的解决方法为那些需要将地图分割成的区域。


解决方案

如果我理解正确的,问题是如何解析上面的CSV文件。



每个行(除了第一个用头)可以与下面的类来表示> 类MapEntry
{
公共字符串描述{搞定;组; }
公共字符串名称{;组; }
公共字符串标签{搞定;组; }
公开的IEnumerable<&经纬度GT; InnerCoordinates {搞定;组; }
公开的IEnumerable<&经纬度GT; OuterCoordinates {搞定;组; }
}

请注意在内蒙古坐标。它们是由 outerBoundaryIs XML中的代表(必填)和 innerBoundaryIs (可选)的元素。



一个侧面说明:在您的文章中高地行不正确 - 你似乎修剪线的一部分,导致不正确的XML(< outerBoundaryIs> ...< / innerBoundaryIs> )。



下面是一个不解析的代码:

 静态的IEnumerable< ; MapEntry> ParseMap(字符串csvFile)
{
从File.ReadLines(csvFile)线返回.Skip(1)
让令牌= line.Split(新[] {','},4 )
让xmlToken =令牌[3]
让XMLTEXT = xmlToken.Substring(1 xmlToken.Length - 2)
让xmlRoot = XElement.Parse(XMLTEXT)
选择新MapEntry
{
说明=令牌[0],
名称=令牌[1],
标签=令牌[2],
InnerCoordinates = GetCoordinates(xmlRoot.Element (innerBoundaryIs)),
OuterCoordinates = GetCoordinates(xmlRoot.Element(outerBoundaryIs)),
};
}

静态的IEnumerable<&经纬度GT; GetCoordinates(节点的XElement)
{
如果(节点== NULL)返回Enumerable.Empty<&经纬度GT;();
VAR元= node.Element(线性环)元素(坐标);从令牌
返回在element.Value.Split('')
让值= token.Split('')
选择新的经纬度(XmlConvert.ToDouble(值[0]), XmlConvert.ToDouble(值[1]));
}



我觉得代码是自我解释。要提到的唯一的细节是:



 让令牌= line.Split(新[] {','},4) 

下面我们使用 string.Split < A HREF =htt​​ps://msdn.microsoft.com/en-us/library/c1bs0eda(v=vs.110).aspx相对=nofollow>超载,可以让我们的指定。子的最大数目返回的,从而避免了处理XML令牌内的逗号的陷阱



 让XMLTEXT = xmlToken.Substring(1 xmlToken.Length  -  2)

$ ; b
$ b

这条从XML标记报价



最后,对于你的情况示例用法:

  
{
的PolylineOptions几何=新的PolylineOptions()
的foreach(VAR的foreach(在ParseMap(csv_file_full_path)VAR项)在entry.OuterCoordinates项)
geometry.Add(项目)
折线折线= mMap.AddPolyline(几何)
}



更新:为了使Xamarin快乐(如前所述在评论),更换 File.ReadLines 与下面的助手打电话呼叫:

 静态的IEnumerable<串GT; readlines方法(字符串路径)
{
变种SR =新的StreamReader(Assets.Open(路径));

{
串线;
,而((行= sr.ReadLine())!= NULL)
收益率的回报线;
}
终于{sr.Dispose(); }
}


In Xamarin google maps for Android using C# you can create polygons like so based on this tutorial:

    public void OnMapReady(GoogleMap googleMap)
    {
        mMap = googleMap;
        PolylineOptions geometry = new PolylineOptions()
        .Add(new LatLng(37.35, -37.0123))
        .Add(new LatLng(37.35, -37.0123))
        .Add(new LatLng(37.35, -37.0123));


        Polyline polyline = mMap.AddPolyline(geometry);

    }

However I have downloaded a CSV file from my Fusion Table Layer from google maps as I think this might be the easiest option to work with polygon/polyline data. The output looks like this:

    description,name,label,geometry
    ,Highland,61,"<Polygon><outerBoundaryIs><LinearRing><coordinates>-5.657018,57.3352 -5.656396,57.334463 -5.655076,57.334556 -5.653439,57.334477 -5.652366,57.334724 -5.650064,57.334477 -5.648096,57.335082 -5.646846,57.335388 -5.644733,57.335539 -5.643309,57.335428 -5.641981,57.335448 -5.640451,57.33578 -5.633217,57.339118 -5.627278,57.338921 -5.617161,57.337649 -5.607948,57.341015 -5.595812,57.343583 -5.586043,57.345373 -5.583581,57.350648 -5.576851,57.353609 -5.570088,57.354017 -5.560732,57.354102 -5.555254,57.354033 -5.549713,57.353146 -5.547766,57.352275 -5.538932,57.352255 -5.525891,57.356217 -5.514888,57.361865 -5.504272,57.366027 -5.494515,57.374515 -5.469829,57.383765 -5.458661,57.389781 -5.453695,57.395033 -5.454057,57.402943 -5.449189,57.40731 -5.440583,57.411447 -5.436133,57.414616 -5.438312,57.415474 -5.438628,57.417955 -5.440956,57.417909 -5.444013,57.414976 -5.450778,57.421362 -5.455035,57.422333 -5.462081,57.420719 -5.468775,57.416975 -5.475205,57.41135 -5.475976,57.409117 -5.47705,57.407092 -5.478101,57.406056 -5.478901,57.40536 -5.479489,57.404534 -5.480051,57.403782 -5.481036,57.403107 -5.484538,57.402102 -5.485647,57.401856 -5.487358,57.401287 -5.488709,57.400962 -5.490175,57.400616 -5.491116,57.400176 -5.493832,57.399318 -5.495279,57.399134 -5.496726,57.39771 -5.498724,57.396836 -5.49974,57.396314 -5.501317,57.39627 -5.502869,57.395426</coordinates></LinearRing></innerBoundaryIs></Polygon>"
    ,Strathclyde,63,"<Polygon><outerBoundaryIs><LinearRing><coordinates>-5.603129,56.313564 -5.603163,56.312536 -5.603643,56.311794 -5.601467,56.311875 -5.601038,56.312481 -5.600697,56.313489 -5.60071,56.31535 -5.60159,56.316107 -5.600729,56.316598 -5.598625,56.316058 -5.596203,56.317477 -5.597024,56.318119 -5.596095,56.318739 -5.595432,56.320116 -5.589343,56.322469 -5.584888,56.325178 -5.582907,56.327169 -5.581414,56.327472 -5.581435,56.326663 -5.582355,56.325602 -5.581515,56.323891 -5.576993,56.331062 -5.57886,56.331475 -5.57676,56.334449 -5.572748,56.335689 -5.569012,56.338143 -5.564802,56.342113 -5.555237,56.346668 -5.551214,56.347448 -5.547651,56.346391 -5.54444,56.344945 -5.541247,56.345945 -5.539099,56.349674 -5.533874,56.34763 -5.525195,56.342888 -5.523518,56.345066 -5.52345,56.346605 -5.526417,56.354361 -5.535455,56.353681 -5.537463,56.35508 -5.536035,56.356271 -5.538923,56.357205 -5.53891,56.359336 -5.539952,56.361491 -5.538102,56.36372 -5.535934,56.36567 -5.53392,56.367705 -5.531369,56.369729 -5.529853,56.371022 -5.532371,56.371274 -5.534177,56.371708 -5.532846,56.373256 -5.529845,56.37496 -5.527675,56.375327 -5.528531,56.375995 -5.526732,56.376343 -5.525442,56.377809 -5.524739,56.379843 -5.526069,56.380561</coordinates></LinearRing></innerBoundaryIs></Polygon>"

I uploaded a KML file to Google Maps Fusion Table Layer, it then created the map. I then went File>Download>CSV and it gave me the above example.

I have added this csv file to my assets folder of my xamarin android google map app and my question would be because LatLng takes two doubles as its input, is there a way I could input the above data from the csv file into this method and if so how?

Not sure how to read the above csv and then extract the <coordinates> and then add those coordinates as new LatLng in the example code above?

If you notice however the coordinates are split into lat and lng and then the next latlng is seperated by a space -5.657018,57.3352 -5.656396,57.334463.

Sudo code (this may or may not require xamarin or android experience and may just require C#/Linq):

Read CSV var sr = new StreamReader(Read csv from Asset folder);
Remove description,name,label,geometry
Foreach line in CSV
  Extract Item that contains double qoutes
     Foreach Item Remove Qoutes and <Polygon><outerBoundaryIs><LinearRing><coordinates> from start and end
         Foreach item seperated by a space Extract coordinates
       (This will now leave a long list of 37.35,-37.0123 coordinates for each line)
        Place in something like this maybe?:

    public class Row
    {
        public double Lat { get; set; }
        public double Lng { get; set; }

        public Row(string str)
        {
            string[] separator = { "," };
            var arr = str.Split(separator, StringSplitOptions.None);
            Lat = Convert.ToDouble(arr[0]);
            Lng = Convert.ToDouble(arr[1]);
        }
    }


    private void OnMapReady()
    var rows = new List<Row>();

      Foreach name/new line
         PolylineOptions geometry = new PolylineOptions()
           ForEach (item in rows) //not sure how polyline options will take a foreach
            .Add(New LatLng(item.Lat, item.Lng))
         Polyline polyline = mMap.AddPolyline(geometry);

As there is no way of using Fusion Table Layers in Xamarin Android with Google Maps API v2 this may provide a quick and easier workaround for those that need to split maps into regions.

解决方案

If I understand correctly, the question is how to parse the above CSV file.

Each line (except the first one with headers) can be represented with the following class:

class MapEntry
{
    public string Description { get; set; }
    public string Name { get; set; }
    public string Label { get; set; }
    public IEnumerable<LatLng> InnerCoordinates { get; set; }
    public IEnumerable<LatLng> OuterCoordinates { get; set; }
}

Note the Inner and Outer coordinates. They are represented inside the XML by outerBoundaryIs (required) and innerBoundaryIs (optional) elements.

A side note: the Highland line in your post is incorrect - you seem to trimmed part of the line, leading to incorrect XML (<outerBoundaryIs>...</innerBoundaryIs>).

Here is the code that does the parsing:

static IEnumerable<MapEntry> ParseMap(string csvFile)
{
    return from line in File.ReadLines(csvFile).Skip(1)
           let tokens = line.Split(new[] { ',' }, 4)
           let xmlToken = tokens[3]
           let xmlText = xmlToken.Substring(1, xmlToken.Length - 2)
           let xmlRoot = XElement.Parse(xmlText)
           select new MapEntry
           {
               Description = tokens[0],
               Name = tokens[1],
               Label = tokens[2],
               InnerCoordinates = GetCoordinates(xmlRoot.Element("innerBoundaryIs")),
               OuterCoordinates = GetCoordinates(xmlRoot.Element("outerBoundaryIs")),
           };
}

static IEnumerable<LatLng> GetCoordinates(XElement node)
{
    if (node == null) return Enumerable.Empty<LatLng>();
    var element = node.Element("LinearRing").Element("coordinates");
    return from token in element.Value.Split(' ')
           let values = token.Split(',')
           select new LatLng(XmlConvert.ToDouble(values[0]), XmlConvert.ToDouble(values[1]));
}

I think the code is self explanatory. The only details to be mentioned are:

let tokens = line.Split(new[] { ',' }, 4)

Here we use the string.Split overload that allows us to specify the maximum number of substrings to return, thus avoiding the trap of processing the commas inside the XML token.

and:

let xmlText = xmlToken.Substring(1, xmlToken.Length - 2)

which strips the quotes from the XML token.

Finally, a sample usage for your case:

foreach (var entry in ParseMap(csv_file_full_path))
{
    PolylineOptions geometry = new PolylineOptions()
    foreach (var item in entry.OuterCoordinates)
        geometry.Add(item)
    Polyline polyline = mMap.AddPolyline(geometry);
}

UPDATE: To make Xamarin happy (as mentioned in the comments), replace the File.ReadLines call with a call to the following helper:

static IEnumerable<string> ReadLines(string path)
{
    var sr = new StreamReader(Assets.Open(path));
    try
    {
        string line;
        while ((line = sr.ReadLine()) != null)
            yield return line; 
    }
    finally { sr.Dispose(); }
}

这篇关于从CSV文件(融合表和KML的解决方法)提取数据的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆