1

我现在正在做一个 windows phone 项目,需要向 web 服务请求一些 json 数据。如果 json 结构类似于 [Dictionary1, Dictionary2, Dictionary3 ] 那么,DataContractJsonSerializer 工作正常。但是下一个请求我会得到一个复杂的 json 数据,它不起作用。像 [ [字典 1]、[字典 2]、[字典 3] ]

真实数据是:

    [

        [{"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。有人知道如何解决吗?非常感谢。

4

2 回答 2

1

问题可能是因为您的类创建,在结束之前检查您处理解析结果的模型类。或者,如果您需要帮助添加更多信息,例如模型类的结构、用于解析 json 的代码等。这里似乎什么都没有完成。Json.Net 将完成所有技巧,您唯一需要做的就是正确构建您的类类型.. 享受编码

于 2012-03-30T13:28:49.307 回答
1

在 Olli Saarikivi 的帮助下,问题得以解决。征得他的许可,在此处发布他的解决方案,以防其他人需要它。

// 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;
}
于 2012-04-02T16:57:11.447 回答