简体   繁体   English

用Newtonsoft.Json反序列化

[英]Deserialize with Newtonsoft.Json

I'm a tester learning C# and REST service testing both new to me...... I have a JSON response like this 我是一名测试人员,正在学习C#和REST服务测试,这对我来说都是新手……我有这样的JSON响应

{ "results" : [
    {
        "address_components" : [
        {
            "long_name" : "1600",
            "short_name" : "1600",
            "types" : [ "street_number" ]
        },
        {
            "long_name" : "Amphitheatre Parkway",
            "short_name" : "Amphitheatre Pkwy",
            "types" : [ "route" ]
        },
        {
            "long_name" : "Mountain View",
            "short_name" : "Mountain View",
            "types" : [ "locality", "political" ]
        },
        {
            "long_name" : "Santa Clara County",
            "short_name" : "Santa Clara County",
            "types" : [ "administrative_area_level_2", "political" ]
        },
        {
            "long_name" : "California",
            "short_name" : "CA",
            "types" : [ "administrative_area_level_1", "political" ]
        },
        {
            "long_name" : "United States",
            "short_name" : "US",
            "types" : [ "country", "political" ]
        },
        {
            "long_name" : "94043",
            "short_name" : "94043",
            "types" : [ "postal_code" ]
        }
     ],
     "formatted_address" : "1600 Amphitheatre Pkwy, Mountain View, CA 94043, USA",
     "geometry" : {
        "location" : {
           "lat" : 37.4223434,
           "lng" : -122.0843689
        },
        "location_type" : "ROOFTOP",
        "viewport" : {
           "northeast" : {
              "lat" : 37.42369238029149,
              "lng" : -122.0830199197085
           },
           "southwest" : {
              "lat" : 37.42099441970849,
              "lng" : -122.0857178802915
           }
        }
     },
     "place_id" : "ChIJ2eUgeAK6j4ARbn5u_wAGqWA",
     "types" : [ "street_address" ]
  }
],
"status" : "OK"
} 

and going to deserialize it to object and only need "lat" and "lng" in geometry / location 并将其反序列化为对象,并且在几何/位置仅需要“ lat”和“ lng”

My code look like 我的代码看起来像

JObject myMap = JObject.Parse(response.Content);
IList<JToken> mylist = myMap["results"][0]["geometry"].Children().ToList();`

 IList<location> spots = new List<location>();
foreach (JToken spot in mylist)
{
    Console.WriteLine("\nthe spots are :\t:"+ spot.ToString());
    location somesopt = JsonConvert.DeserializeObject<location>(spot.ToString());
    Console.WriteLine("\n the lat is :\t" + somesopt.lat.ToString());
    Console.WriteLine("\n the lat is :\t" + somesopt.lng.ToString());
}

and my objects are ......... 我的对象是......

   public class location
{
    public double lat { get; set; }
    public double lng { get; set; }
}

public class geopost
{
    public location geometry;
}

The problem is always I get JsonSerializationException at json deseserializobject I try changing many permutation of defining mylist but could not get it write ....what wrong am I doing..? 问题始终是我在json deseserializobject上收到JsonSerializationException,我尝试更改定义mylist的许多排列,但无法将其写成..我在做什么错.. ??

when use same structure of code for "Long_name" and "short_name" at address component it works fine. 在地址部分对“ Long_name”和“ short_name”使用相同的代码结构时,它可以正常工作。 I understand that address component is array and geometry / location are objects. 我知道地址部分是数组,几何/位置是对象。 But how do you handle it? 但是您如何处理呢?

I do the same as sugested by DavidG, but I generate the clases by copying the JSON into the clipboard and then on VS I go to menú Edit -> Paste Special -> Paste JSON as Classes . 我所做的操作与DavidG的建议相同,但是我通过将JSON复制到剪贴板中来生成clase,然后在VS上,进入菜单Edit -> Paste Special -> Paste JSON as Classes

That generates the classes needed to deseralize: 生成反序列化所需的类:

public class Rootobject
{
    public Result[] results { get; set; }
    public string status { get; set; }
}

public class Result
{
    public Address_Components[] address_components { get; set; }
    public string formatted_address { get; set; }
    public Geometry geometry { get; set; }
    public string place_id { get; set; }
    public string[] types { get; set; }
}

(...)

And same deserialization approach: 和相同的反序列化方法:

var data = JsonConvert.DeserializeObject<RootObject>(json);

Why not deserialise to a proper class structure? 为什么不反序列化为适当的类结构? Something like this: 像这样:

public class AddressComponent
{
    public string long_name { get; set; }
    public string short_name { get; set; }
    public List<string> types { get; set; }
}

public class Location
{
    public double lat { get; set; }
    public double lng { get; set; }
}

public class Northeast
{
    public double lat { get; set; }
    public double lng { get; set; }
}

public class Southwest
{
    public double lat { get; set; }
    public double lng { get; set; }
}

public class Viewport
{
    public Northeast northeast { get; set; }
    public Southwest southwest { get; set; }
}

public class Geometry
{
    public Location location { get; set; }
    public string location_type { get; set; }
    public Viewport viewport { get; set; }
}

public class Result
{
    public List<AddressComponent> address_components { get; set; }
    public string formatted_address { get; set; }
    public Geometry geometry { get; set; }
    public string place_id { get; set; }
    public List<string> types { get; set; }
}

public class RootObject
{
    public List<Result> results { get; set; }
    public string status { get; set; }
}

Then deserialise like this: 然后像这样反序列化:

var data = JsonConvert.DeserializeObject<RootObject>(json);

Now you can operate directly on your object hierarchy: 现在,您可以直接在对象层次结构上进行操作:

foreach (var result in data.results)
{
    var lat = result.geometry.location.lat;
}

PS I generated the class hierarchy from json2csharp.com PS我从json2csharp.com生成了类层次结构

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM