using System; using System.Collections.Generic; using System.Data; using System.Data.Common; using System.Linq; using System.Reflection; using System.Reflection.Emit; using System.Text; namespace SqlSugar { public static class ReflectionExtensions { /// /// 检查输入值是否为空 /// /// /// static bool isNullOrEmpty(object val) { if (val == null) return true; if (val.ToString() == "") return true; return false; } /// Delegate to set an arbitrary property at runtime. /// the object instance whose property will be modified. /// public delegate void FastPropertySetHandler(object target, object parameter); /// /// 用于存放SetPropertySetter的Dictionary /// private static Dictionary dictSetter = new Dictionary(); /// /// 快速设置成员属性 /// /// /// public static FastPropertySetHandler GetPropertySetter(PropertyInfo propInfo) { lock (dictSetter) { if (dictSetter.ContainsKey(propInfo)) return dictSetter[propInfo]; // generates a dynamic method to generate a FastPropertySetHandler delegate DynamicMethod dynamicMethod = new DynamicMethod(string.Empty, null, new Type[] { typeof(object), typeof(object) }, propInfo.DeclaringType.Module); ILGenerator ilGenerator = dynamicMethod.GetILGenerator(); // loads the object into the stack ilGenerator.Emit(OpCodes.Ldarg_0); // loads the parameter from the stack ilGenerator.Emit(OpCodes.Ldarg_1); // cast to the proper type (unboxing if needed) EmitCastToReference(ilGenerator, propInfo.PropertyType); // calls the setter ilGenerator.EmitCall(OpCodes.Callvirt, propInfo.GetSetMethod(), null); // terminates the call ilGenerator.Emit(OpCodes.Ret); // converts the DynamicMethod to a FastPropertyGetHandler delegate to get the property FastPropertySetHandler setter = (FastPropertySetHandler)dynamicMethod.CreateDelegate(typeof(FastPropertySetHandler)); dictSetter.Add(propInfo, setter); return setter; } } /// Emits the cast to a reference, unboxing if needed. /// The MSIL generator. /// The type to cast. private static void EmitCastToReference(ILGenerator ilGenerator, System.Type type) { if (type.IsValueType) { ilGenerator.Emit(OpCodes.Unbox_Any, type); } else { ilGenerator.Emit(OpCodes.Castclass, type); } } /// /// 根据数据类型将指定数据进行相应转换 /// /// /// /// public static object ConvertForType(object value, Type type) { if (Convert.IsDBNull(value) || (value == null)) { return null; } string typeName = type.FullName.ToString(); if (type == typeof(System.Nullable)) { value = Convert.ToUInt16(value); } else if (type == typeof(System.Nullable)) { value = Convert.ToUInt32(value); } else if (type == typeof(System.Nullable)) { value = Convert.ToUInt64(value); } else if (type == typeof(System.Nullable)) { value = Convert.ToInt32(value); } else if (type == typeof(System.Nullable)) { value = Convert.ToInt64(value); } else if (type == typeof(System.Nullable)) { value = Convert.ToDateTime(value); } switch (typeName) { case "System.String": if (!isNullOrEmpty(value)) value = value.ToString(); else value = string.Empty; break; case "System.Boolean": if (!isNullOrEmpty(value)) value = Convert.ToBoolean(value); break; case "System.Int16": if (!isNullOrEmpty(value)) value = Convert.ToInt16(value); break; case "System.Int32": if (!isNullOrEmpty(value)) value = Convert.ToInt32(value); else value = 0; break; case "System.Int64": if (!isNullOrEmpty(value)) value = Convert.ToInt64(value); else value = 0; break; case "System.Double": if (!isNullOrEmpty(value)) value = Convert.ToDouble(value); else value = 0.00; break; case "System.Float": if (!isNullOrEmpty(value)) value = Convert.ToDouble(value); else value = 0.00; break; case "System.Single": if (!isNullOrEmpty(value)) value = Convert.ToSingle(value); break; case "System.Decimal": if (!isNullOrEmpty(value)) value = Convert.ToDecimal(value); else value = 0.00; break; case "System.DateTime": if (!isNullOrEmpty(value)) value = Convert.ToDateTime(value); else value = DateTime.MinValue; break; } return value; } /// /// 设置属性值 /// /// /// /// public static void SetPropertyValue(object obj, PropertyInfo property, object value) { if (property.CanWrite) { var propertySetter = GetPropertySetter(property); value = ConvertForType(value, property.PropertyType); if (value != null) { if (property.PropertyType.BaseType.Name == "Enum") { propertySetter(obj, Enum.Parse(property.PropertyType, value.ToString())); } else propertySetter(obj, value); } } } /// /// 设置属性值 /// /// /// /// public static void SetPropertyValue(object obj, string propertyName, object value) { SetPropertyValue(obj.GetType(), obj, propertyName, value); } /// /// 设置属性值 /// /// /// /// /// public static void SetPropertyValue(Type type, object obj, string propertyName, object value) { PropertyInfo property = type.GetProperty(propertyName); if (property != null) { SetPropertyValue(obj, property, value); } } public static Type GetTypeInfo(this Type typeInfo) { return typeInfo; } public static Type[] GetGenericArguments(this Type type) { var reval = type.GetTypeInfo().GetGenericArguments(); return reval; } public static bool IsGenericType(this Type type) { var reval = type.GetTypeInfo().IsGenericType; return reval; } public static PropertyInfo[] GetProperties(this Type type) { var reval = type.GetTypeInfo().GetProperties(); return reval; } public static PropertyInfo GetProperty(this Type type, string name) { var reval = type.GetTypeInfo().GetProperty(name); return reval; } public static FieldInfo GetField(this Type type, string name) { var reval = type.GetTypeInfo().GetField(name); return reval; } public static bool IsEnum(this Type type) { var reval = type.GetTypeInfo().IsEnum; return reval; } public static MethodInfo GetMethod(this Type type, string name) { var reval = type.GetTypeInfo().GetMethod(name); return reval; } public static MethodInfo GetMethod(this Type type, string name, Type[] types) { var reval = type.GetTypeInfo().GetMethod(name, types); return reval; } public static ConstructorInfo GetConstructor(this Type type, Type[] types) { var reval = type.GetTypeInfo().GetConstructor(types); return reval; } public static bool IsValueType(this Type type) { return type.GetTypeInfo().IsValueType; } public static bool IsEntity(this Type type) { return type.GetTypeInfo().IsClass; } public static Type ReflectedType(this MethodInfo method) { return method.ReflectedType; } } }