Windows Phone, Как десериализовать JSON, который вложил массив - PullRequest
1 голос
/ 30 марта 2012

Сейчас я делаю проект для Windows Phone, и мне нужно запросить у веб-службы некоторые данные JSON. если структура JSON похожа [Dictionary1, Dictionary2, Dictionary3 ] затем DataContractJsonSerializer работает нормально. но в следующем запросе я получу сложные данные JSON, это не работает. лайк [ [Dictionary1], [Dictionary2], [Dictionary3] ]

реальные данные:

    [

        [{"length":5734.042,"duration":1680,"legs":
            [
                {"length":685,"duration":555.42,"type":"walk","locs":

                    [

                        {"coord":{"x":2546445,"y":6675512},"arrTime":"201203290959","depTime":"201203290959","name":null},
                        {"coord":{"x":2546433.8,"y":6675498.3},"arrTime":"201203291000","depTime":"201203291000","name":"Teekkaripolku"}
                    ]
                },


                {"length":4158,"duration":420,"type":"5","code":"2506  2","locs":
                    [
                        {"coord":{"x":2546168,"y":6674959},"arrTime":"201203291009","depTime":"201203291009","name":"Alvar Aallon puisto","code":"2222235","shortCode":"E2226","stopAddress":"Otaniementie"},
                        {"coord":{"x":2546337,"y":6674857},"arrTime":"201203291009","depTime":"201203291009","name":"Dipoli","code":"2222204","shortCode":"E2204","stopAddress":"Otaniementie"}
                    ]
                }
            ]
        }],


        [{"length":5734.042,"duration":1680,"legs":
            [
                {"length":685,"duration":555.42,"type":"1", "code":"1111", "locs":
                    [
                        {"coord":{"x":2546445,"y":6675512},"arrTime":"201203290952","depTime":"201203290952","name":null},
                        {"coord":{"x":2546433.8,"y":6675498.3},"arrTime":"201203290953","depTime":"201203290953","name":"Teekkaripolku"}
                    ]
                },
                {"length":4158,"duration":420,"type":"5","code":"2194  2","locs":
                    [   {"coord":{"x":2546168,"y":6674959},"arrTime":"201203291002","depTime":"201203291002","name":"Alvar Aallon puisto","code":"2222235","shortCode":"E2226","stopAddress":"Otaniementie"},
                        {"coord":{"x":2546337,"y":6674857},"arrTime":"201203291002","depTime":"201203291002","name":"Dipoli","code":"2222204","shortCode":"E2204","stopAddress":"Otaniementie"}
                    ]
                }
            ]
        }]

    ]

и модели класса:

[DataContract]
public class RouteList
{
    [DataMember]
    public List<Route> oneRoute;

}

---
    [DataContract]
public class Route
{
    [DataMember(Name = "length", IsRequired = true)]
    public Double length { get; set; }

    [DataMember(Name = "duration", IsRequired = true)]
    public Double duration { get; set; }

   [DataMember(Name = "legs", IsRequired = true)] 
    public List<Leg> legs { get; set; }
}

----
    [DataContract] 
public class Leg
{
    [DataMember(Name = "length", IsRequired = true)]
    public Double length { get; set; }

    [DataMember(Name = "duration", IsRequired = true)]
    public Double duration { get; set; }

    [DataMember(Name = "type", IsRequired = true)]
    public String type { get; set; }

    [DataMember(Name = "code", IsRequired = false)]
    public String code { get; set; }

    [DataMember(Name = "locs", IsRequired = true)]
    public List<Loc> locs { get; set; }

    [DataMember(Name = "shape", IsRequired = false)]
    public String shape { get; set; }
}

-----

    [DataContract] 
public class Loc
{
    [DataMember(Name = "coord", IsRequired = true)]
    public String coord { get; set; }

    [DataMember(Name = "arrTime", IsRequired = true)]
    public String arrTime { get; set; }

    [DataMember(Name = "depTime", IsRequired = true)]
    public String depTime { get; set; }

    [DataMember(Name = "name", IsRequired = true)]
    public String name { get; set; }

    [DataMember(Name = "code", IsRequired = false)]
    public String code { get; set; }

    [DataMember(Name = "shortCode", IsRequired = false)]
    public String shortCode { get; set; }

    [DataMember(Name = "stopAddress", IsRequired = false)]
    public String stopAddress { get; set; }

}

и код десериализации:

 System.IO.MemoryStream mStream = new System.IO.MemoryStream(System.Text.Encoding.UTF8.GetBytes(e.Result));
 DataContractJsonSerializer serializer = new DataContractJsonSerializer(typeof(List<RouteList>));
 result = (List<RouteList>)serializer.ReadObject(mStream);

Я пробовал DataContractJsonSerializer и json.NET. но не удалось. и наиболее вероятная проблема - вложенные массивы, модель: RouteList. кто-нибудь знает как это исправить? Большое спасибо.

Ответы [ 2 ]

1 голос
/ 02 апреля 2012

с помощью Олли Саарикиви проблема решена. с его разрешения опубликуйте его решение здесь, на случай, если оно понадобится кому-либо еще.

// The request response handler

var routeResults = new List<CompoundRoute>();

if (e.Result.Trim().Length != 0)
{
  JArray json = JArray.Parse(e.Result);

  foreach (var token in json)
 {
    var routeArray = token as JArray;
    if (routeArray != null)
    {
        var compoundRoute = new CompoundRoute { Routes = new Route[routeArray.Count] };
        for (int i = 0; i < compoundRoute.Routes.Length; ++i)
        {
            compoundRoute.Routes[i] = new Route(routeArray[i]);
        }
        routeResults.Add(compoundRoute);
    }
 }
}

 // The data model

 [DataContract]
 public class CompoundRoute
 {
    private static readonly Route[] EmptyRoutes = new Route[0];

    public CompoundRoute()
    {
        Routes = EmptyRoutes;
    }

    [DataMember]
    public Route[] Routes;
 }

[DataContract]
public class Route
{
   public Route(JToken token)
   {
    Length = token.Value<double>("length");

    int durationSeconds = token.Value<int>("duration");
    Duration = TimeSpan.FromSeconds(durationSeconds);

    JArray legTokens = token["legs"] as JArray;
    if (legTokens != null)
    {
        Legs = new Leg[legTokens.Count];
        for (int i = 0; i < Legs.Length; ++i)
        {
            Legs[i] = new Leg(legTokens[i]);
        }
    }
  }

  [DataMember]
  public double Length;
  [DataMember]
  public TimeSpan Duration;
  [DataMember]
  public Leg[] Legs;
}

[DataContract]
public class Leg
{
  public Leg(JToken token)
  {
    Length = token.Value<double>("length");

    double durationSeconds = token.Value<double>("duration");
    Duration = TimeSpan.FromSeconds((int)Math.Round(durationSeconds));

    Type = token.Value<string>("type");

    string lineCode = token.Value<string>("code");
    if (lineCode != null)
    {
        Line = App.Cache.GetOrCreate(lineCode, () => new Line(lineCode));
    }

    if (Type == "12") // Commuter trains
    {
        Line.ShortName = Utils.RemoveLeadingNumbers(Line.ShortName);
    }

    JArray locTokens = token["locs"] as JArray;
    if (locTokens != null)
    {
        Locs = new LegLocation[locTokens.Count];
        for (int i = 0; i < Locs.Length; ++i)
        {
            Locs[i] = new LegLocation(locTokens[i]);
        }
    }
    else
    {
        Locs = new LegLocation[0];
    }

    JArray shapeTokens = token["shape"] as JArray;
    if (shapeTokens != null)
    {
        Shape = new ReittiCoordinate[shapeTokens.Count];
        for (int i = 0; i < Shape.Length; ++i)
        {
            var shapeToken = shapeTokens[i];
            double x = shapeToken.Value<double>("x");
            double y = shapeToken.Value<double>("y");
            var coordinate = new ReittiCoordinate(y, x);
            Shape[i] = coordinate;
        }
    }
}

[DataMember]
public double Length;
[DataMember]
public TimeSpan Duration;
[DataMember]
public string Type;
[DataMember]
public Line Line;
[DataMember]
public LegLocation[] Locs;
[DataMember]
public ReittiCoordinate[] Shape;
}

[DataContract]
public class LegLocation
{
  public LegLocation(JToken token)
  {
    var coordToken = token["coord"];
    double x = coordToken.Value<double>("x");
    double y = coordToken.Value<double>("y");
    Coord = new ReittiCoordinate(y, x);

    string arrTimeString = token.Value<string>("arrTime");
    ArrTime = DateTime.ParseExact(arrTimeString, "yyyyMMddHHmm", null);

    string depTimeString = token.Value<string>("depTime");
    DepTime = DateTime.ParseExact(depTimeString, "yyyyMMddHHmm", null);

    Name = token.Value<string>("name");
 }

 [DataMember]
 public ReittiCoordinate Coord;
 [DataMember]
 public DateTime ArrTime;
 [DataMember]
 public DateTime DepTime;
 [DataMember]
 public string Name;
}
1 голос
/ 30 марта 2012

Возможно, проблема связана с созданием вашего класса. Прежде чем завершить проверку класса вашей модели, который обрабатывает проанализированный вами результат.Или, если вам нужна помощь, добавьте больше информации, например, структуру вашего модельного класса, код, который вы использовали для анализа json и т. Д. Здесь, кажется, ничего не завершено.Json.Net сделает все трюки, единственное усилие, которое вам нужно предпринять, это правильное построение вашего типа класса. Наслаждайтесь кодированием

...