public static string GetObjectDescription(PropertyInfoEx prop)
        {
            if (prop == null)
            {
                return(string.Empty);
            }

            if (!string.IsNullOrWhiteSpace(prop.GetDesc()))
            {
                return(prop.GetDesc());
            }
            var descs = prop.PropertyInfo.GetCustomAttributes(typeof(PropertyDescriptionAttribute), true);

            if (descs == null || descs.Length == 0)
            {
                return(string.Empty);
            }

            string tname = string.Empty;

            try
            {
                if (prop.PropertyInfo.ReflectedType.IsGenericType)
                {
                    //tname = prop.ReflectedType.GetGenericArguments().First().ReflectedType.Name;
                    tname = ((Type[])prop.PropertyInfo.ReflectedType.Eval("GenericTypeArguments")).First().Name;
                }
                return((descs[0] as PropertyDescriptionAttribute).Desc.Replace("<T>", tname));
            }
            catch
            {
                return((descs[0] as PropertyDescriptionAttribute).Desc.Replace("<T>", "对象"));
            }
        }
        public static object Eval(this object o, PropertyInfoEx propertyInfo)
        {
            if (o == null)
            {
                return(null);
            }
            if (propertyInfo == null)
            {
                return(null);
            }

            if (propertyInfo.IsSetGetValueMethed)
            {
                return(propertyInfo.GetValueMethed(o));
            }

            ParameterExpression instance = Expression.Parameter(
                typeof(object), "instance");
            Expression instanceCast = Expression.Convert(
                instance, propertyInfo.PropertyInfo.ReflectedType);
            Expression propertyAccess = Expression.Property(
                instanceCast, propertyInfo.PropertyInfo);
            UnaryExpression castPropertyValue = Expression.Convert(
                propertyAccess, typeof(object));

            Expression <Func <object, object> > lamexpress =
                Expression.Lambda <Func <object, object> >(
                    castPropertyValue, instance);

            propertyInfo.GetValueMethed = lamexpress.Compile();

            return(propertyInfo.GetValueMethed(o));
        }
        public static void SetValue(this object o, PropertyInfoEx property, object val)
        {
            if (property.IsSetSetValueMethed)
            {
                try
                {
                    property.SetValueMethed(o, val);
                }
                catch
                {
                    try
                    {
                        property.SetValueMethed(o, Convert.ChangeType(val, property.PropertyInfo.PropertyType));
                    }
                    catch
                    {
                        throw new Exception(string.Format("字符串转换失败,无法从{0}转到{1}:{2}", val.GetType().Name, property.PropertyInfo.PropertyType.Name, val));
                    }
                }
                return;
            }

            var tp = o.GetType();
            ParameterExpression instance     = Expression.Parameter(typeof(object), "instance");
            ParameterExpression valParameter = Expression.Parameter(typeof(object), "val");

            //转换为真实类型
            var instanceCast     = Expression.Convert(instance, tp);
            var valParameterCast = Expression.Convert(valParameter, property.PropertyInfo.PropertyType);


            var body       = Expression.Call(instanceCast, property.PropertyInfo.GetSetMethod(), valParameterCast);
            var lamexpress = Expression.Lambda <Action <object, object> >(body, instance, valParameter).Compile();

            property.SetValueMethed = lamexpress;
            try
            {
                lamexpress(o, val);
            }
            catch
            {
                try
                {
                    lamexpress(o, Convert.ChangeType(val, property.PropertyInfo.PropertyType));
                }
                catch
                {
                    throw new Exception(string.Format("字符串转换失败,无法从{0}转到{1}:{2}", val.GetType().Name, property.PropertyInfo.PropertyType.Name, val));
                }
            }
        }
        //public static object EvalDrect(this object o, PropertyInfo prop)
        //{
        //    if (o == null)
        //        return null;
        //    if (prop == null)
        //        return null;
        //    return prop.GetValue(o, null);
        //}

        public static Func <object, object> GetGetValueFunc(Type type, PropertyInfoEx propertyInfo)
        {
            ParameterExpression instance = Expression.Parameter(
                typeof(object), "instance");
            Expression instanceCast = Expression.Convert(
                instance, propertyInfo.PropertyInfo.ReflectedType);
            Expression propertyAccess = Expression.Property(
                instanceCast, propertyInfo.PropertyInfo);
            UnaryExpression castPropertyValue = Expression.Convert(
                propertyAccess, typeof(object));

            Expression <Func <object, object> > lamexpress =
                Expression.Lambda <Func <object, object> >(
                    castPropertyValue, instance);

            return(lamexpress.Compile());
        }
        public static Action <object, object> GetSetValueFunc(Type type, PropertyInfoEx property)
        {
            ParameterExpression instance     = Expression.Parameter(typeof(object), "instance");
            ParameterExpression valParameter = Expression.Parameter(typeof(object), "val");

            //转换为真实类型
            var instanceCast     = Expression.Convert(instance, type);
            var valParameterCast = Expression.Convert(valParameter, property.PropertyInfo.PropertyType);


            var body       = Expression.Call(instanceCast, property.PropertyInfo.GetSetMethod(), valParameterCast);
            var lamexpress = Expression.Lambda <Action <object, object> >(body, instance, valParameter).Compile();

            //property.SetValueMethed = lamexpress;

            return(lamexpress);
        }