使用C#中的Json.NET计算JSON字符串中的元素数

时间:2012-04-03 20:48:00

标签: c# json json.net

我有一个如下所示的JSON字符串:

{
"package1": {
    "type": "envelope",
    "quantity": 1,
    "length": 6,
    "width": 1,
    "height": 4
},
"package2": {
    "type": "box",
    "quantity": 2,
    "length": 9,
    "width": 9,
    "height": 9
}
}

我正在使用Json.NET LINQ to JSON功能来处理我的JSON字符串,但我想知道如何找到节点/元素/键的总数(我真的不知道该怎么称呼它们)在我的字符串中。例如,上面的字符串有package1和package2所以我想知道如何让它返回整数2.有时我可能只有一个包,在这种情况下,我希望它返回整数1.其他我可能有20个包(在这种情况下,我希望它能返回20个)。

我的JObject看起来像这样:

JObject o = JObject.Parse(myJsonString);

有什么想法吗?谢谢你的帮助。

5 个答案:

答案 0 :(得分:20)

JObject jObj = (JObject)JsonConvert.DeserializeObject(myJsonString);
int count = jObj.Count;

<强>奖金:

dynamic jObj = JsonConvert.DeserializeObject(myJsonString);

foreach (var package in jObj)
{
    Console.WriteLine("{0} {1}", package.First.type, package.First.quantity);
}

答案 1 :(得分:0)

递归版本(使用原始值计算所有属性)

遇到这个问题,试图用Google递归计数JObject值,却没有发现很多其他问题,所以我想我也会对这个问题提出自己的看法

int CountJTokenProperties(JToken token)
{
    var sum = 0;

    if (token.Type == JTokenType.Object)
    {
        foreach (var child in token.Value<JObject>())
        {
            sum += CountJTokenProperties(child.Value);
        }
    }
    else if (token.Type == JTokenType.Array)
    {
        foreach (var child in token.Value<JArray>())
        {
            sum += CountJTokenProperties(child);
        }
    }
    else
    {
        sum += 1;
    }

    return sum;
}

.Value<JObject>().Value<JArray>()可能有更好的替代方法,但这似乎可行。

尤其是对于具有可变样本数据的nunit测试,我希望这样做,并希望确保其正确反序列化。确定一种简单的检查方法是C#对象上有多少非默认值,而JsonConvert则具有该功能:

public int CountNonDefaultProperties(object obj)
{
    // Let JsonConvert do the work of stripping out default values
    var serialized = JsonConvert.SerializeObject(obj, new JsonSerializerSettings
    {
        DefaultValueHandling = DefaultValueHandling.Ignore
    });

    // Recurse into the json structure, which is much simpler than C# Object structure
    var jObj = JObject.Parse(serialized);

    return CountJTokenProperties(jObj);
}

请注意,DefaultValueHandling.Ignore保留默认值是数组的一部分,因此,如果您想要该功能,则需要以其他方式或其他方式对数组项进行计数,该活动留给读者 >

https://dotnetfiddle.net/XIZCvh

答案 2 :(得分:0)

使用Cinchoo ETL-一个开放源代码库,您可以使用流方法来解析输入,从而以较少的内存开销轻松地进行节点计数。因此,它也可以处理大文件。

getType()

希望有帮助。

答案 3 :(得分:0)

 string json= "{
"package1": {
"type": "envelope",
"quantity": 1,
"length": 6,
"width": 1,
"height": 4
 },
 "package2": {
 "type": "box",
 "quantity": 2,
 "length": 9,
 "width": 9,
 "height": 9
 }
 }"; 

 dynamic stuff;
 int count;
 stuff = JsonConvert.DeserializeObject(json);
 foreach(JProperty s in stuff){

  count++;
  }

  Console.WriteLine(count.ToString());

如果Count属性对您而言不起作用,请尝试执行此操作。确保您的C#版本为4.0或更高版本,因为那时已添加了dynamic关键字。

答案 4 :(得分:-3)

在JQuery $ .ajax中,您将收到一个数组,遍历元素并得到总和。