コード例 #1
0
        private object DeserializeToClass(string input, Type type)
        {
            if (input.StartsWith("{", StringComparison.Ordinal) == true && input.EndsWith("}", StringComparison.Ordinal) == true)
            {
                string source = input;
                input = input.Substring(1, input.Length - 2);
                Dictionary <string, string> keyValue = new Dictionary <string, string>();
                foreach (var temp in JsonHelper.ItemReader(input))
                {
                    string key;
                    string value;
                    JsonHelper.ItemSpliter(temp, out key, out value);
                    if (key.StartsWith("\"", StringComparison.Ordinal) == true && key.EndsWith("\"", StringComparison.Ordinal) == true)
                    {
                        key = key.Substring(1, key.Length - 2);
                    }
                    else
                    {
                        throw new JsonDeserializeException(source, type);
                    }
                    if (keyValue.ContainsKey(key) == false)
                    {
                        keyValue.Add(key, value);
                    }
                    else
                    {
                        throw new JsonDeserializeException(source, type);
                    }
                }
                #region 匿名类。
                if (type.Name.Contains("AnonymousType") == true && string.IsNullOrEmpty(type.Namespace) == true)
                {
                    // 获取匿名类唯一构造函数。
                    ConstructorInfo constructor = type.GetConstructors().Single();

                    // 获取匿名类构造函数的参数。
                    ParameterInfo[] parameters = constructor.GetParameters();

                    // 存放反序列化的参数。
                    List <object> args = new List <object>();

                    foreach (ParameterInfo parameter in parameters)
                    {
                        // 参数名字。
                        string parameterName = parameter.Name;
                        if (keyValue.ContainsKey(parameterName) == true)
                        {
                            // json 中存在对应的值。
                            args.Add(DeserializeToObject(keyValue[parameterName], parameter.ParameterType));
                        }
                        else
                        {
                            // json 中不存在对应的值,填充类型的默认值。
                            Type parameterType = parameter.ParameterType;
                            if (parameterType.IsValueType == true)
                            {
                                args.Add(Activator.CreateInstance(parameterType));
                            }
                            else
                            {
                                args.Add(null);
                            }
                        }
                    }

                    // 执行构造函数。
                    return(constructor.Invoke(args.ToArray()));
                }
                #endregion
                object instance;
                try
                {
                    instance = Activator.CreateInstance(type, true);
                }
                catch
                {
                    var constructors = type.GetConstructors(BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance).OrderBy(temp => temp.IsPublic == false).ThenBy(temp => temp.GetParameters().Length);
                    var constructor  = constructors.ElementAt(0);
                    instance = constructor.Invoke(new object[constructor.GetParameters().Length]);
                }
                #region 字段。
                FieldInfo[] fields;
                if (JsonHelper._typeFields.TryGetValue(type, out fields) == false)
                {
                    fields = type.GetFields(BindingFlags.Public | BindingFlags.Static | BindingFlags.NonPublic | BindingFlags.Instance);
                    if (JsonHelper._typeFields.ContainsKey(type) == false)
                    {
                        lock (JsonHelper._typeFields)
                        {
                            if (JsonHelper._typeFields.ContainsKey(type) == false)
                            {
                                JsonHelper._typeFields.Add(type, fields);
                            }
                        }
                    }
                }
                foreach (FieldInfo field in fields)
                {
                    JsonAttribute attribute = field.GetCustomAttributes(typeof(JsonAttribute), false).FirstOrDefault() as JsonAttribute;
                    if (attribute != null)
                    {
                        if (field.IsPublic == false && attribute.ProcessNonPublic == false)
                        {
                            continue;
                        }
                        string name;
                        object value;
                        if (string.IsNullOrEmpty(attribute.Name) == true)
                        {
                            name = field.Name;
                        }
                        else
                        {
                            name = attribute.Name;
                        }
                        if (keyValue.ContainsKey(name) == true)
                        {
                            if (attribute.Converter != null)
                            {
                                JsonConverter converter = Activator.CreateInstance(attribute.Converter) as JsonConverter;
                                if (converter != null)
                                {
                                    bool skip = false;
                                    value = converter.Deserialize(keyValue[name], field.FieldType, ref skip);
                                    if (skip == true)
                                    {
                                        continue;
                                    }
                                }
                                else
                                {
                                    throw new JsonDeserializeException(source, type);
                                }
                            }
                            else
                            {
                                value = DeserializeToObject(keyValue[name], field.FieldType);
                            }
                            field.SetValue(instance, value);
                        }
                    }
                    else
                    {
                        if (field.IsPublic == false)
                        {
                            continue;
                        }
                        string name = field.Name;
                        if (keyValue.ContainsKey(name) == true)
                        {
                            field.SetValue(instance, DeserializeToObject(keyValue[name], field.FieldType));
                        }
                    }
                }
                #endregion
                #region 属性。
                PropertyInfo[] properties;
                if (JsonHelper._typeProperties.TryGetValue(type, out properties) == false)
                {
                    properties = type.GetProperties(BindingFlags.Public | BindingFlags.Static | BindingFlags.NonPublic | BindingFlags.Instance);
                    if (JsonHelper._typeProperties.ContainsKey(type) == false)
                    {
                        lock (JsonHelper._typeProperties)
                        {
                            if (JsonHelper._typeProperties.ContainsKey(type) == false)
                            {
                                JsonHelper._typeProperties.Add(type, properties);
                            }
                        }
                    }
                }
                foreach (PropertyInfo property in properties)
                {
                    if (property.GetIndexParameters().Length == 0)
                    {
                        JsonAttribute attribute = property.GetCustomAttributes(typeof(JsonAttribute), false).FirstOrDefault() as JsonAttribute;
                        if (attribute != null)
                        {
                            if (property.CanWrite == false && attribute.ProcessNonPublic == false)
                            {
                                continue;
                            }
                            MethodInfo setMethod = property.GetSetMethod(true);
                            if (setMethod == null)
                            {
                                continue;
                            }
                            string name;
                            object value;
                            if (string.IsNullOrEmpty(attribute.Name) == true)
                            {
                                name = property.Name;
                            }
                            else
                            {
                                name = attribute.Name;
                            }
                            if (keyValue.ContainsKey(name) == true)
                            {
                                if (attribute.Converter != null)
                                {
                                    JsonConverter converter =
                                        Activator.CreateInstance(attribute.Converter) as JsonConverter;
                                    if (converter != null)
                                    {
                                        bool skip = false;
                                        value = converter.Deserialize(keyValue[name], property.PropertyType, ref skip);
                                        if (skip == true)
                                        {
                                            continue;
                                        }
                                    }
                                    else
                                    {
                                        throw new JsonDeserializeException(source, type);
                                    }
                                }
                                else
                                {
                                    value = DeserializeToObject(keyValue[name], property.PropertyType);
                                }

                                setMethod.Invoke(instance, new object[1] {
                                    value
                                });
                            }
                        }
                        else
                        {
                            if (property.CanWrite == false)
                            {
                                continue;
                            }
                            string name = property.Name;
                            if (keyValue.ContainsKey(name) == true)
                            {
                                property.SetValue(instance, DeserializeToObject(keyValue[name], property.PropertyType), null);
                            }
                        }
                    }
                }
                #endregion
                return(instance);
            }
            else
            {
                throw new JsonDeserializeException(input, type);
            }
        }
コード例 #2
0
        private string SerializeClass(object obj)
        {
            Type          type   = obj.GetType();
            List <string> values = new List <string>();

            #region 字段
            FieldInfo[] fields;
            if (JsonHelper._typeFields.TryGetValue(type, out fields) == false)
            {
                fields = type.GetFields(BindingFlags.Public | BindingFlags.Static | BindingFlags.NonPublic | BindingFlags.Instance);
                if (JsonHelper._typeFields.ContainsKey(type) == false)
                {
                    lock (JsonHelper._typeFields)
                    {
                        if (JsonHelper._typeFields.ContainsKey(type) == false)
                        {
                            JsonHelper._typeFields.Add(type, fields);
                        }
                    }
                }
            }
            foreach (var field in fields)
            {
                JsonAttribute attribute = field.GetCustomAttributes(typeof(JsonAttribute), false).FirstOrDefault() as JsonAttribute;
                string        name;
                object        value;
                string        valueString;
                if (attribute != null)
                {
                    // 不序列化此字段。
                    if (attribute.Ignore == true)
                    {
                        continue;
                    }
                    // 非公有字段且不序列化。
                    if (field.IsPublic == false && attribute.ProcessNonPublic == false)
                    {
                        continue;
                    }
                    value = field.GetValue(obj);
                    // 不序列化 null 字段。
                    if (attribute.IgnoreNull == true && value == null)
                    {
                        continue;
                    }
                    // 字段是否必须。
                    if (attribute.Required == true && value == null)
                    {
                        throw new ArgumentNullException(field.Name, "该字段不能为 null。");
                    }
                    // 检查数量约束。
                    IEnumerable <object> enumerable = value as IEnumerable <object>;
                    if (enumerable != null)
                    {
                        if (attribute.CountLessThan > -1 && enumerable.Count() >= attribute.CountLessThan)
                        {
                            throw JsonCountException.CreateLessThanException(value, attribute.CountLessThan);
                        }
                        if (attribute.CountGreaterThan > -1 && enumerable.Count() <= attribute.CountGreaterThan)
                        {
                            throw JsonCountException.CreateGreaterThanException(value, attribute.CountGreaterThan);
                        }
                    }
                    // 使用自定义序列化。
                    if (attribute.Converter != null)
                    {
                        JsonConverter converter = (JsonConverter)Activator.CreateInstance(attribute.Converter);
                        bool          skip      = false;
                        valueString = converter.Serialize(value, field.FieldType, ref skip);
                        if (skip == true)
                        {
                            continue;
                        }
                    }
                    else
                    {
                        valueString = SerializeObject(value);
                    }
                    // 使用自定义映射名字。
                    if (string.IsNullOrEmpty(attribute.Name) == false)
                    {
                        name = "\"" + attribute.Name + "\"";
                    }
                    else
                    {
                        name = "\"" + field.Name + "\"";
                    }
                }
                else
                {
                    if (field.IsPublic == false)
                    {
                        continue;
                    }
                    name        = "\"" + field.Name + "\"";
                    value       = field.GetValue(obj);
                    valueString = SerializeObject(value);
                }
                values.Add(name + ":" + valueString);
            }
            #endregion
            #region 属性
            PropertyInfo[] properties;
            if (JsonHelper._typeProperties.TryGetValue(type, out properties) == false)
            {
                properties = type.GetProperties(BindingFlags.Public | BindingFlags.Static | BindingFlags.NonPublic | BindingFlags.Instance);
                if (JsonHelper._typeProperties.ContainsKey(type) == false)
                {
                    lock (JsonHelper._typeProperties)
                    {
                        if (JsonHelper._typeProperties.ContainsKey(type) == false)
                        {
                            JsonHelper._typeProperties.Add(type, properties);
                        }
                    }
                }
            }
            foreach (var property in properties)
            {
                if (property.GetIndexParameters().Length == 0)
                {
                    JsonAttribute attribute = property.GetCustomAttributes(typeof(JsonAttribute), false).FirstOrDefault() as JsonAttribute;
                    string        name;
                    object        value;
                    string        valueString;
                    if (attribute != null)
                    {
                        // 不序列化此属性。
                        if (attribute.Ignore == true)
                        {
                            continue;
                        }
                        // 非公有属性且不序列化。
                        if (property.CanRead == false && attribute.ProcessNonPublic == false)
                        {
                            continue;
                        }
                        value = property.GetGetMethod(true).Invoke(obj, null);
                        // 不序列化 null 属性。
                        if (attribute.IgnoreNull == true && value == null)
                        {
                            continue;
                        }
                        // 属性是否必须。
                        if (attribute.Required == true && value == null)
                        {
                            throw new ArgumentNullException(property.Name, "该属性不能为 null。");
                        }
                        // 检查数量约束。
                        IEnumerable <object> enumerable = value as IEnumerable <object>;
                        if (enumerable != null)
                        {
                            if (attribute.CountLessThan > -1 &&
                                enumerable.Count() >= attribute.CountLessThan)
                            {
                                throw JsonCountException.CreateLessThanException(value,
                                                                                 attribute.CountLessThan);
                            }
                            if (attribute.CountGreaterThan > -1 &&
                                enumerable.Count() <= attribute.CountGreaterThan)
                            {
                                throw JsonCountException.CreateGreaterThanException(value,
                                                                                    attribute.CountGreaterThan);
                            }
                        }
                        // 使用自定义序列化。
                        if (attribute.Converter != null)
                        {
                            JsonConverter converter = (JsonConverter)Activator.CreateInstance(attribute.Converter);
                            bool          skip      = false;
                            valueString = converter.Serialize(value, property.PropertyType, ref skip);
                            if (skip == true)
                            {
                                continue;
                            }
                        }
                        else
                        {
                            valueString = SerializeObject(value);
                        }
                        // 使用自定义映射名字。
                        if (string.IsNullOrEmpty(attribute.Name) == false)
                        {
                            name = "\"" + attribute.Name + "\"";
                        }
                        else
                        {
                            name = "\"" + property.Name + "\"";
                        }
                    }
                    else
                    {
                        if (property.CanRead == false)
                        {
                            continue;
                        }
                        name        = "\"" + property.Name + "\"";
                        value       = property.GetValue(obj, null);
                        valueString = SerializeObject(value);
                    }
                    values.Add(name + ":" + valueString);
                }
            }
            #endregion
            return("{" + string.Join(",", values) + "}");
        }