在C#中解析JSON的最有效方法

时间:2013-04-18 16:20:40

标签: c# asp.net json

我想知道在C#中解析JSON的最有效方法是什么?而且效率我指的是响应时间较短的那个。我试图使用几种方法解析大量数据,这两种方法的响应时间都很长。谁能告诉我以下方法之间的区别?是否有一种替代方案可以让我以较低的响应时间进行解析?

选项1:

HttpWebRequest request = WebRequest.Create(jsonURL) as HttpWebRequest;
using (HttpWebResponse response = request.GetResponse() as HttpWebResponse)
{
    if (response.StatusCode != HttpStatusCode.OK)
        throw new Exception(String.Format(
        "Server error (HTTP {0}: {1}).",
        response.StatusCode,
        response.StatusDescription));
    DataContractJsonSerializer jsonSerializer = new DataContractJsonSerializer(typeof(obj));
    object objResponse = jsonSerializer.ReadObject(response.GetResponseStream());
}  

选项2:

var json = new WebClient().DownloadString(jsonURL);
using (MemoryStream ms = new MemoryStream(Encoding.Unicode.GetBytes(json)))
{
    DataContractJsonSerializer jsonSerializer = new DataContractJsonSerializer(typeof(obj));
    object objResponse = jsonSerializer.ReadObject(ms);
}  

5 个答案:

答案 0 :(得分:13)

您可以在以下链接中找到比较结果。

测试的库:

http://sagistech.blogspot.com/2010/03/parsing-twitter-json-comparing-c.html

  • Json.NET - 一个流行的C#JSON库。
  • Gapi.NET - Gapi.NET不是JSON解析库,但它包含JSON解析例程。
  • Procurios - 又一个C#JSON库。另请参阅此博客文章,了解如何使用它来解析Twiter数据。
  • JavaScriptSerializer - .NET 3.5内置JSON解析器。
  • DataContractJsonSerializer - .NET 3.5内置JSON解析器。
  • AjaxPro - 一个C#AJAX库。

enter image description here


<强>更新

根据Matt Johnson的评论

添加了此信息

http://theburningmonk.com/2011/11/performance-test-json-serializers-part-ii/

答案 1 :(得分:1)

第一种方法有机会减少数据副本。但我很难相信这两种方法都会产生可衡量的差异。您的实际成本将是网络成本。

答案 2 :(得分:1)

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;


namespace Example
{
public static class JavascriptSerializator
{
    /// <summary>
    /// Serializes object to JSON from Microsoft
    /// </summary>
    /// <param name="objectForSerialization"></param>
    /// <returns></returns>
    public static string SerializeMJSON(this object objectForSerialization)
    {
        try
        {
            System.Web.Script.Serialization.JavaScriptSerializer s = new System.Web.Script.Serialization.JavaScriptSerializer();

            return s.Serialize(objectForSerialization);
        }
        catch (Exception ex)
        {
            /// Handle exception and throw it ...
        }

    }

    /// <summary>
    /// Deserializes object from Microsoft JSON string
    /// </summary>
    /// <typeparam name="T"></typeparam>
    /// <param name="str"></param>
    /// <returns></returns>
    public static T DeserializeMJSON<T>(this string str)
    {
        try
        {
            System.Web.Script.Serialization.JavaScriptSerializer s = new System.Web.Script.Serialization.JavaScriptSerializer();

            return s.Deserialize<T>(str);
        }
        catch (Exception ex)
        {
            //// Handle the exception here...
        }

    }
}

}

答案 3 :(得分:1)

仍然处于早期阶段,但我在Json.NET之上构建了一个代码生成器,它消除了反射并加速了反序列化4倍。

结帐CGbR JSON target

[DataContract]
public partial class Root
{
    [DataMember]
    public int Number { get; set; }

    [DataMember]
    public Partial[] Partials { get; set; }

    [DataMember]
    public IList<ulong> Numbers { get; set; }
}

将生成一个部分类:

public Root FromJson(JsonReader reader)
{
    while (reader.Read())
    {
        // Break on EndObject
        if (reader.TokenType == JsonToken.EndObject)
            break;

        // Only look for properties
        if (reader.TokenType != JsonToken.PropertyName)
            continue;

        switch ((string) reader.Value)
        {
            case "Number":
                reader.Read();
                Number = Convert.ToInt32(reader.Value);
                break;

            case "Partials":
                reader.Read(); // Read token where array should begin
                if (reader.TokenType == JsonToken.Null)
                    break;
                var partials = new List<Partial>();
                while (reader.Read() && reader.TokenType == JsonToken.StartObject)
                    partials.Add(new Partial().FromJson(reader));
                Partials = partials.ToArray();
                break;

            case "Numbers":
                reader.Read(); // Read token where array should begin
                if (reader.TokenType == JsonToken.Null)
                    break;
                var numbers = new List<ulong>();
                while (reader.Read() && reader.TokenType != JsonToken.EndArray)
                    numbers.Add(Convert.ToUInt64(reader.Value));
                Numbers = numbers;
                break;

        }
    }

    return this;
}

答案 4 :(得分:0)

出于好奇,我有JSON.NET 5.0 r8和我自己的(只有~500行代码)玩具JSON解析器吃各种JSON文件大小,有或没有循环,从几十个角色球场到一个180 MB的JSON文件,例如“真实”数据。

示例数据(包括12mb JSON但不包括可在其他地方找到的180mb)以及附带的详细信息,例如从流解析到反序列化为POCO(强类型)对象的示例,可在此处找到:

https://github.com/ysharplanguage/FastJsonParser

'希望它有所帮助。

P.S。 很好的链接,知道,顺便说一下,Chamika已经在他的评论中提供了。

修改

在我忘记之前(或者只是在被忽略的情况下),这里必须知道/必须阅读,IMO,关于强调CLR的大对象堆的重要性感谢您的代码消耗的JSON的流式读取,尤其是在Web服务器环境的上下文中:

http://insidethecpu.wordpress.com/2013/06/19/json-parsing/

P.P.S。 (因此,在Program.cs中测试/展示我上面链接的玩具解析器的最后一次测试)

“HTH!