2016-07-11 4 views
-1

눈보라에서 경매 데이터 (6 메가 바이트 JSON 파일) 다운로드, 디코드에,이에 오류를 추적 할 수있는 동안 : 직렬화 또는 직렬화 복원이를 사용하는 동안디코딩 큰 JSON 파일

"오류 . JSON JavaScriptSerializer 문자열의 길이는 maxJsonLength 속성에 설정된 값을 초과 \ 연구 \ nParameter 이름 :. 입력 "

을 내가 구문 분석 JSON의 일부로서 (20MB의 말을 maxJsonLength을 변경할 수 있습니다 어떻게 그 다음 큰 클래스)?

public sealed class DynamicJsonConverter : JavaScriptConverter 
{ 
    public override object Deserialize(IDictionary<string, object> dictionary, Type type, JavaScriptSerializer serializer) 
    { 
     if (dictionary == null) 
      throw new ArgumentNullException("dictionary"); 

     return type == typeof(object) ? new DynamicJsonObject(dictionary) : null; 
    } 

    public override IDictionary<string, object> Serialize(object obj, JavaScriptSerializer serializer) 
    { 
     throw new NotImplementedException(); 
    } 

    public override IEnumerable<Type> SupportedTypes 
    { 
     get { return new ReadOnlyCollection<Type>(new List<Type>(new[] { typeof(object) })); } 
    } 

    #region Nested type: DynamicJsonObject 

    private sealed class DynamicJsonObject : DynamicObject 
    { 
     private readonly IDictionary<string, object> _dictionary; 

     public DynamicJsonObject(IDictionary<string, object> dictionary) 
     { 
      if (dictionary == null) 
       throw new ArgumentNullException("dictionary"); 
      _dictionary = dictionary; 
     } 

     public override string ToString() 
     { 
      var sb = new StringBuilder("{"); 
      ToString(sb); 
      return sb.ToString(); 
     } 

     private void ToString(StringBuilder sb) 
     { 
      var firstInDictionary = true; 
      foreach (var pair in _dictionary) 
      { 
       if (!firstInDictionary) 
        sb.Append(","); 
       firstInDictionary = false; 
       var value = pair.Value; 
       var name = pair.Key; 
       if (value is string) 
       { 
        sb.AppendFormat("{0}:\"{1}\"", name, value); 
       } 
       else if (value is IDictionary<string, object>) 
       { 
        new DynamicJsonObject((IDictionary<string, object>)value).ToString(sb); 
       } 
       else if (value is ArrayList) 
       { 
        sb.Append(name + ":["); 
        var firstInArray = true; 
        foreach (var arrayValue in (ArrayList)value) 
        { 
         if (!firstInArray) 
          sb.Append(","); 
         firstInArray = false; 
         if (arrayValue is IDictionary<string, object>) 
          new DynamicJsonObject((IDictionary<string, object>)arrayValue).ToString(sb); 
         else if (arrayValue is string) 
          sb.AppendFormat("\"{0}\"", arrayValue); 
         else 
          sb.AppendFormat("{0}", arrayValue); 

        } 
        sb.Append("]"); 
       } 
       else 
       { 
        sb.AppendFormat("{0}:{1}", name, value); 
       } 
      } 
      sb.Append("}"); 
     } 

     public override bool TryGetMember(GetMemberBinder binder, out object result) 
     { 
      if (!_dictionary.TryGetValue(binder.Name, out result)) 
      { 
       // Return null to avoid exception. The caller can check for null this way... 
       result = null; 
       return true; 
      } 

      result = WrapResultObject(result); 
      return true; 
     } 

     public override bool TryGetIndex(GetIndexBinder binder, object[] indexes, out object result) 
     { 
      if (indexes.Length == 1 && indexes[0] != null) 
      { 
       if (!_dictionary.TryGetValue(indexes[0].ToString(), out result)) 
       { 
        // Return null to avoid exception. The caller can check for null this way... 
        result = null; 
        return true; 
       } 

       result = WrapResultObject(result); 
       return true; 
      } 

      return base.TryGetIndex(binder, indexes, out result); 
     } 

     private static object WrapResultObject(object result) 
     { 
      var dictionary = result as IDictionary<string, object>; 
      if (dictionary != null) 
       return new DynamicJsonObject(dictionary); 

      var arrayList = result as ArrayList; 
      if (arrayList != null && arrayList.Count > 0) 
      { 
       return arrayList[0] is IDictionary<string, object> 
        ? new List<object>(arrayList.Cast<IDictionary<string, object>>().Select(x => new DynamicJsonObject(x))) 
        : new List<object>(arrayList.Cast<object>()); 
      } 

      return result; 
     } 
    } 

    #endregion 
} 

또는 호출 방법에

:

public static dynamic DecodeJson(this string str) 
    { 
     var serializer = new JavaScriptSerializer(); 
     serializer.RegisterConverters(new[] { new DynamicJsonConverter() }); 
     dynamic result = null; 
     try 
     { 
      result = serializer.Deserialize(str, typeof(object)); 
     } catch (ArgumentException ae) 
     { 
      Log.Output(ae.InnerException.Message); 
     } 
     return result; 
    } 
+1

사람이 downvote에 의해 구동-A를하지, 난에 desrialization 클래스를 게시 늦게 모든 질문으로 보인다. 질문 자체에 문제가있는 경우 문제가 무엇인지에 대해 설명하여 해결/설명 될 수 있도록하십시오. –

+0

대답이 아니지만, C#을 사용하기 때문에 JIL이나 JSON.NET과 같은 서드 파티 json 시리얼 라이저 중 하나를 고려해 볼 수 있습니다. 특히이 같은 대형 파일의 경우 훨씬 더 빠릅니다. 분명히 의존성이 필요합니다. –

+2

JavaScriptSerializer 속성 MaxJsonLength에 대한 오류 메시지가 매우 명확합니다. 문서를 간략하게 살펴보면 해결 방법을 알 수있었습니다. 나는 downvote에 놀라지 않는다 –

답변

5

당신은 JSON 문자열의 JavaScriptSerializer.MaxJsonLength Property

최대 길이를 수정해야합니다. 기본값은 2097152 자이고, 유니 코드 문자열 데이터 4MB에 해당하는 입니다.

public static dynamic DecodeJson(this string str) 
{ 
    var serializer = new JavaScriptSerializer(); 
    serializer.MaxJsonLength = Int.MaxValue; // The value of this constant is 2,147,483,647 
    serializer.RegisterConverters(new[] { new DynamicJsonConverter() }); 
    dynamic result = null; 
    try 
    { 
     result = serializer.Deserialize(str, typeof(object)); 
    } catch (ArgumentException ae) 
    { 
     Log.Output(ae.InnerException.Message); 
    } 
    return result; 
} 
+0

우수. 고맙습니다 :) –