代码之家  ›  专栏  ›  技术社区  ›  Alexandr

序列化中出现System.OverflowException

  •  2
  • Alexandr  · 技术社区  · 11 年前

    我有一些类用于解析web响应:

    [DataContract]
    public abstract class GYResponse 
    {
        [DataMember(Name = "code")]
        public int Code { get; set; }
        [DataMember(Name = "message")]
        public string Message { get; set; }
    }
    
    [DataContract]
    public class ResponseGetUser : GYResponse
    {
        [DataMember(Name = "result")]
        public GYUser Result { get; set; }
    }
    
    [DataContract]
    public class ResponseGetVenue : GYResponse
    {
        [DataMember(Name = "result")]
        public GYVenue Result { get; set; }
    }
    

    我使用 DataContractJsonSerializer :

    GYResponse response_obj = request.Creater.CreateResponseObj(); 
    //CreateResponseObj() return ResponseGetUser, ResponseGetVenue etc
    
    using (MemoryStream stream = new MemoryStream(Encoding.Unicode.GetBytes(gyResponse)))
    {
        DataContractJsonSerializer serializer = new DataContractJsonSerializer(response_obj.GetType());                   
        response_obj = (GYResponse)serializer.ReadObject(stream);       
    }
    

    我有 "System.OverflowException" 排队:

    response_obj = (GYResponse)serializer.ReadObject(stream); 
    

    /checked编译器选项已关闭。并且 ReadObject 无法引发此异常。

    但如果我重写类,那么它就起作用了:

    [DataContract]
    public abstract class GYResponse 
    {
    
    }
    
    [DataContract]
    public class ResponseGetUser : GYResponse
    {
        [DataMember(Name = "result")]
        public GYUser Result { get; set; }
        [DataMember(Name = "code")]
        public int Code { get; set; }
        [DataMember(Name = "message")]
        public string Message { get; set; }
    }
    
    [DataContract]
    public class ResponseGetVenue : GYResponse
    {
        [DataMember(Name = "result")]
        public GYVenue Result { get; set; }
        [DataMember(Name = "code")]
        public int Code { get; set; }
        [DataMember(Name = "message")]
        public string Message { get; set; }
    }
    

    我知道这是一个模糊的问题,但不明白问题出在哪里。什么时候可以抛出这个异常?

    更新异常信息:

    消息:

     There was an error deserializing the object of type GotYou.RequesterService.ResponseGetInfo. Value was either too large or too small for an Int32.
    

    内部异常:

    at System.Number.ParseInt32(String s, NumberStyles style, NumberFormatInfo info)
       at System.String.System.IConvertible.ToInt32(IFormatProvider provider)
       at System.Convert.ChangeType(Object value, Type conversionType, IFormatProvider provider)
       at System.Runtime.Serialization.Json.DataContractJsonSerializer.ConvertObjectToPrimitiveDataContract(DataContract contract, Object value, XmlObjectSerializerReadContextComplexJson context)
       at System.Runtime.Serialization.Json.DataContractJsonSerializer.ConvertObjectToDataContract(DataContract contract, Object value, XmlObjectSerializerReadContextComplexJson context)
       at System.Runtime.Serialization.Json.ObjectToDataContractConverter.ReadClassDataContractMembers(DataContractJsonSerializer serializer, ClassDataContract dataContract, Dictionary`2 deserialzedValue, Object newInstance, XmlObjectSerializerReadContextComplexJson context)
       at System.Runtime.Serialization.Json.ObjectToDataContractConverter.ReadClassDataContractMembers(DataContractJsonSerializer serializer, ClassDataContract dataContract, Dictionary`2 deserialzedValue, Object newInstance, XmlObjectSerializerReadContextComplexJson context)
       at System.Runtime.Serialization.Json.ObjectToDataContractConverter.ConvertDictionaryToClassDataContract(DataContractJsonSerializer serializer, ClassDataContract dataContract, Dictionary`2 deserialzedValue, XmlObjectSerializerReadContextComplexJson context)
       at System.Runtime.Serialization.Json.DataContractJsonSerializer.ConvertObjectToDataContract(DataContract contract, Object value, XmlObjectSerializerReadContextComplexJson context)
       at System.Runtime.Serialization.Json.ObjectToDataContractConverter.ReadClassDataContractMembers(DataContractJsonSerializer serializer, ClassDataContract dataContract, Dictionary`2 deserialzedValue, Object newInstance, XmlObjectSerializerReadContextComplexJson context)
       at System.Runtime.Serialization.Json.ObjectToDataContractConverter.ConvertDictionaryToClassDataContract(DataContractJsonSerializer serializer, ClassDataContract dataContract, Dictionary`2 deserialzedValue, XmlObjectSerializerReadContextComplexJson context)
       at System.Runtime.Serialization.Json.DataContractJsonSerializer.ConvertObjectToDataContract(DataContract contract, Object value, XmlObjectSerializerReadContextComplexJson context)
       at System.Runtime.Serialization.Json.ObjectToDataContractConverter.ReadClassDataContractMembers(DataContractJsonSerializer serializer, ClassDataContract dataContract, Dictionary`2 deserialzedValue, Object newInstance, XmlObjectSerializerReadContextComplexJson context)
       at System.Runtime.Serialization.Json.ObjectToDataContractConverter.ConvertDictionaryToClassDataContract(DataContractJsonSerializer serializer, ClassDataContract dataContract, Dictionary`2 deserialzedValue, XmlObjectSerializerReadContextComplexJson context)
       at System.Runtime.Serialization.Json.DataContractJsonSerializer.ConvertObjectToDataContract(DataContract contract, Object value, XmlObjectSerializerReadContextComplexJson context)
       at System.Runtime.Serialization.Json.DataContractJsonSerializer.ReadObject(Stream stream)
    

    StrackTrace公司:

     at System.Runtime.Serialization.Json.DataContractJsonSerializer.ReadObject(Stream stream)
       at GotYou.RequesterService.PostRequester.getResponseCallback(IAsyncResult asynchronousResult)
    

    Json回应:

    {
        "code": 0,
        "message": "",
        "result": {
            "uid": "51da997decaa3ca351000000",
            "url": "",
            "nickname": "Smileman",
            "avatar": "\/img\/profile_pics\/users\/51da997decaa3ca351000000\/cache\/avatar48x48.jpg?lastUpdate=1381215566",
            "age": {
                "number": "22",
                "suffix": "года",
                "birthday": "1991-04-17"
            },
            "sex": 1,
            "aboutself": "",
            "premium": true,
            "isFriend": 3,
            "online": {
                "lastVisit": "7 минут назад",
                "status": true
            },
            "features": {
                "car": false,
                "house": false,
                "cash": false,
                "group": true
            },
            "location": {
                "longitude": 36.570838832,
                "latitude": 50.571069472,
                "timestamp": 1381319677
            },
            "bonuses": 8515,
            "address": "",
            "city": {
                "code": "3100000100000",
                "title": ""
            },
            "cover": "\/img\/profile_pics\/users\/51da997decaa3ca351000000\/cache\/hero480x290.jpg?lastUpdate=1381215566",
            "distance": 63.671441859659,
            "paidServices": {
                "vip": true,
                "theming": true,
                "invisible": false,
                "incognito": false,
                "closed": true
            },
            "regdate": "19.08.2013",
            "purpose": {
                "id": "500fa718ecaa3c6e3b000002",
                "title": ""
            }
        }
    }
    
    1 回复  |  直到 11 年前
        1
  •  4
  •   BartoszKP    11 年前

    这个数字: 3100000100000 中的数据太大 Int32 保持它。的最大正值 国际32 2147483647 。您可以考虑使用 Int64 ( UInt32 也会太小,因为它的范围结束于 4294967295 ).

    然而 code 字段通常被解释为字符串,所以可能 string 数据类型是一个更好的选项,例如:

    [DataMember(Name = "code")]
    public string Code { get; set; }