解析复杂的JSON:多个循环与类

时间:2022-10-18 21:47:51

I have a Json of type :

我有一个类型的Json:

{
"JobProcessors": [
{
  "JobName": "ArchivalJob",
  "IsEnabled": true,
  "Batching": {
    "BatchSize": 0,
    "DegreeOfParallelism": -1
  },
  "Settings": {
    "ArchivalJobCollectionPageSize": 50
  }
},
{
  "JobName": "AuditLogJob",
  "IsEnabled": false,
  "Batching": {
    "BatchSize": 10,
    "DegreeOfParallelism": -1
  },
  "Settings": {}
} 
],  
"ScheduledJobs": [
{
  "JobName": "RemoteStartClientCommandJob",
  "PrimaryAction": {
    "ConnectionString": "#JobProcessorsIntegrationSBConnectionStringValue#",
     "Settings": {
      "LeadTimeInSeconds": "600",
      "MaxSrsJobCount": 25
    }
  },
  "ErrorAction": {
    "ConnectionString": "#PairedJobProcessorIntegrationSBConnectionStringValue#",
    "EntityPath": "remotestartqueue",
    "Settings": {
      "LeadTimeInSeconds": "600",
      "MaxSrsJobCount": 25
    }
  }
}
]  
}

I want to check the "IsEnabled" property for all "JobName" for which come under "JobProcessors" category. In C# what i Have used till now is :

我想检查“JobProcessors”类别下所有“JobName”的“IsEnabled”属性。在C#中,我到目前为止使用的是:

dynamic parsedJson = JsonConvert.DeserializeObject(reader.GetString(1));
foreach (var item in parsedJson)
{
    foreach (var smallitem in item)
    {
        foreach (var tag in smallitem)
        {
            if(tag.IsEnabled.toString()=="true"){
                Console.WriteLine("true");
            }                                 
        }
    }

}

This is giving me correct result except the fact that it also iterates for "ScheduledJobs" . But the main issue is :

这给了我正确的结果,除了它还迭代“ScheduledJobs”。但主要问题是:


Is this the right or most efficient way to do this ? If possible suggest some better method .

这是正确或最有效的方法吗?如果可能建议一些更好的方法。

One that i know of is using classes , but i may not know the json structure beforehand. Also the json is very huge so making classes can be cumbersome !!

我所知道的是使用类,但我可能事先不知道json结构。 json也非常庞大,因此制作课程可能很麻烦!!

2 个解决方案

#1


1  

Given that you are already doing JObject.Parse(jsonstring); to parse your JSON string, you can use SelectTokens() with a JSONPath query to find all "JobName" objects under "JobProcessors":

鉴于你已经在做JObject.Parse(jsonstring);要解析您的JSON字符串,您可以使用带有JSONPath查询的SelectTokens()来查找“JobProcessors”下的所有“JobName”对象:

// I want to check the "IsEnabled" property for all "JobName" for which come under "JobProcessors" 
foreach (var job in root.SelectTokens("..JobProcessors[?(@.JobName)]"))
{
    var isEnabled = (bool?)job["IsEnabled"];
    Debug.WriteLine(string.Format("Job {0}: IsEnabled={1}", job["JobName"], isEnabled));
}

Notes:

笔记:

  • .. is the recursive descent operator: it recursively descends the JToken hierarchy returning each item, subsequently to be matched against the remaining parts of the query string.

    ..是递归下降运算符:它递归地下降返回每个项目的JToken层次结构,随后与查询字符串的其余部分进行匹配。

  • JobProcessors returns values of properties of that name.

    JobProcessors返回该名称的属性值。

  • [?(@.JobName)] returns array items (of JobProcessors in this case) that are objects with a JobName property.

    [?(@。JobName)]返回具有JobName属性的对象的数组项(在本例中为JobProcessors)。

  • (bool?) casts the value of "IsEnabled" to a boolean or null if missing.

    (bool?)将“IsEnabled”的值转换为布尔值,如果缺少则转换为null。

And the output of this is:

而这个的输出是:

Job ArchivalJob: IsEnabled=True
Job AuditLogJob: IsEnabled=False

#2


1  

As in your code snippet we are using two foreach it may take time for large object. So we can do the same thing in a single foreach or if you have some specific node to fetch or search we can use linq, and for this first we need to convert our json object into c# object. For converting Json object to C# you can use this site "http://json2csharp.com/" then we can Deserialize Json object into c#.

在您的代码片段中,我们使用两个foreach,大型对象可能需要一些时间。所以我们可以在一个foreach中做同样的事情,或者如果你有一些特定的节点来获取或搜索我们可以使用linq,为此首先我们需要将我们的json对象转换为c#对象。要将Json对象转换为C#,您可以使用此站点“http://json2csharp.com/”然后我们可以将Json对象反序列化为c#。

It will be something like this

它会是这样的

string jsonString = "your Json Object as string";
        var jsonObject = JsonConvert.DeserializeObject<RootObject>(jsonString);
        foreach (JobProcessor obj in jsonObject.JobProcessors)
        {
            string JobName = obj.JobName;
            bool value=obj.IsEnabled;
        }

And I also converted given Json in c# object if the Json object is same you can directly use these classes.

我还在c#对象中转换了给定的Json,如果Json对象相同,则可以直接使用这些类。

    public class Batching
    {
        public int BatchSize { get; set; }
        public int DegreeOfParallelism { get; set; }
    }

    public class Settings
    {
        public int ArchivalJobCollectionPageSize { get; set; }
    }

    public class JobProcessor
    {
        public string JobName { get; set; }
        public bool IsEnabled { get; set; }
        public Batching Batching { get; set; }
        public Settings Settings { get; set; }
    }

    public class Settings2
    {
        public string LeadTimeInSeconds { get; set; }
        public int MaxSrsJobCount { get; set; }
    }

    public class PrimaryAction
    {
        public string ConnectionString { get; set; }
        public Settings2 Settings { get; set; }
    }

    public class Settings3
    {
        public string LeadTimeInSeconds { get; set; }
        public int MaxSrsJobCount { get; set; }
    }

    public class ErrorAction
    {
        public string ConnectionString { get; set; }
        public string EntityPath { get; set; }
        public Settings3 Settings { get; set; }
    }

    public class ScheduledJob
    {
        public string JobName { get; set; }
        public PrimaryAction PrimaryAction { get; set; }
        public ErrorAction ErrorAction { get; set; }
    }

    public class RootObject
    {
        public List<JobProcessor> JobProcessors { get; set; }
        public List<ScheduledJob> ScheduledJobs { get; set; }
    }

Hope this will help. Thank you

希望这会有所帮助。谢谢

#1


1  

Given that you are already doing JObject.Parse(jsonstring); to parse your JSON string, you can use SelectTokens() with a JSONPath query to find all "JobName" objects under "JobProcessors":

鉴于你已经在做JObject.Parse(jsonstring);要解析您的JSON字符串,您可以使用带有JSONPath查询的SelectTokens()来查找“JobProcessors”下的所有“JobName”对象:

// I want to check the "IsEnabled" property for all "JobName" for which come under "JobProcessors" 
foreach (var job in root.SelectTokens("..JobProcessors[?(@.JobName)]"))
{
    var isEnabled = (bool?)job["IsEnabled"];
    Debug.WriteLine(string.Format("Job {0}: IsEnabled={1}", job["JobName"], isEnabled));
}

Notes:

笔记:

  • .. is the recursive descent operator: it recursively descends the JToken hierarchy returning each item, subsequently to be matched against the remaining parts of the query string.

    ..是递归下降运算符:它递归地下降返回每个项目的JToken层次结构,随后与查询字符串的其余部分进行匹配。

  • JobProcessors returns values of properties of that name.

    JobProcessors返回该名称的属性值。

  • [?(@.JobName)] returns array items (of JobProcessors in this case) that are objects with a JobName property.

    [?(@。JobName)]返回具有JobName属性的对象的数组项(在本例中为JobProcessors)。

  • (bool?) casts the value of "IsEnabled" to a boolean or null if missing.

    (bool?)将“IsEnabled”的值转换为布尔值,如果缺少则转换为null。

And the output of this is:

而这个的输出是:

Job ArchivalJob: IsEnabled=True
Job AuditLogJob: IsEnabled=False

#2


1  

As in your code snippet we are using two foreach it may take time for large object. So we can do the same thing in a single foreach or if you have some specific node to fetch or search we can use linq, and for this first we need to convert our json object into c# object. For converting Json object to C# you can use this site "http://json2csharp.com/" then we can Deserialize Json object into c#.

在您的代码片段中,我们使用两个foreach,大型对象可能需要一些时间。所以我们可以在一个foreach中做同样的事情,或者如果你有一些特定的节点来获取或搜索我们可以使用linq,为此首先我们需要将我们的json对象转换为c#对象。要将Json对象转换为C#,您可以使用此站点“http://json2csharp.com/”然后我们可以将Json对象反序列化为c#。

It will be something like this

它会是这样的

string jsonString = "your Json Object as string";
        var jsonObject = JsonConvert.DeserializeObject<RootObject>(jsonString);
        foreach (JobProcessor obj in jsonObject.JobProcessors)
        {
            string JobName = obj.JobName;
            bool value=obj.IsEnabled;
        }

And I also converted given Json in c# object if the Json object is same you can directly use these classes.

我还在c#对象中转换了给定的Json,如果Json对象相同,则可以直接使用这些类。

    public class Batching
    {
        public int BatchSize { get; set; }
        public int DegreeOfParallelism { get; set; }
    }

    public class Settings
    {
        public int ArchivalJobCollectionPageSize { get; set; }
    }

    public class JobProcessor
    {
        public string JobName { get; set; }
        public bool IsEnabled { get; set; }
        public Batching Batching { get; set; }
        public Settings Settings { get; set; }
    }

    public class Settings2
    {
        public string LeadTimeInSeconds { get; set; }
        public int MaxSrsJobCount { get; set; }
    }

    public class PrimaryAction
    {
        public string ConnectionString { get; set; }
        public Settings2 Settings { get; set; }
    }

    public class Settings3
    {
        public string LeadTimeInSeconds { get; set; }
        public int MaxSrsJobCount { get; set; }
    }

    public class ErrorAction
    {
        public string ConnectionString { get; set; }
        public string EntityPath { get; set; }
        public Settings3 Settings { get; set; }
    }

    public class ScheduledJob
    {
        public string JobName { get; set; }
        public PrimaryAction PrimaryAction { get; set; }
        public ErrorAction ErrorAction { get; set; }
    }

    public class RootObject
    {
        public List<JobProcessor> JobProcessors { get; set; }
        public List<ScheduledJob> ScheduledJobs { get; set; }
    }

Hope this will help. Thank you

希望这会有所帮助。谢谢