zoukankan      html  css  js  c++  java
  • 对System.ComponentModel.DataAnnotations 的学习应用

    摘要

      你还在为了验证一个Class对象中很多数据的有效性而写很多If条件判断吗?我也同样遇到这种问题,不过,最近学了一项新的方法,让我不在写很多if条件做判断,通过给属性标注特性来验证数据规则,从此再也不需要写很多If条件判断了。

      最近写C#项目中的时候,在验证数据的有效性的时候写了很多判断,结果工作量很大,然后就想能实现在类属性上标示验证的特性,来验证数据的有效性,以前听说过,但是从来没有实现过,也很少看到在项目中别人使用过,所以就一直没有研究过,但是最近在写Model的时候需要验证很多数据的有效性,所以就想研究一下。

    需求:将类属性标示一个验证特性,在使用该类的时候验证数据的有效性,

      我是使用了控制台应用程序做测试,首先我的思路是将Class的属性标示上特性,用来验证属性的数据规则,

    这里定义了一个验证特性,主要是来标示属性的最大长度,和当大于最大长度是得提示信息。

        /// <summary>
        /// 指定数据字段中允许的最小和最大字符长度。
        /// </summary>
        public class StringLengthAttribute : Attribute
        {
            /// <summary>
            /// 获取或设置字符串的最大长度。
            /// </summary>
            public int MaximumLength { get; set; }/// <summary>
            /// 消息提示
            /// </summary>
            public string ErrorMessage { get; set; }
    
            /// <summary>
            /// 
            /// </summary>
            /// <param name="maximumLength"></param>
            public StringLengthAttribute(int maximumLength)
            {
                MaximumLength = maximumLength;
            }
    
        }

    这里是用来验证的类

        /// <summary>
        /// 数据模型
        /// </summary>
        public class DataModel : MyIsValid<DataModel>
        {
            /// <summary>
            ////// </summary>
            [StringLength(5, ErrorMessage = "Value最大长度为5")]
            public string Value { get; set; }
        }

    然后我就写了一个基类,统统的在基类中做验证。下面是基类的代码,打算以后所有的需要做验证的类,都继承该基类,将属性标识上特性做验证呢(后来发现更好的办法),写的不好,还请多多指教。

        public class MyIsValid<T> where T : class
        {
    
            //验证信息
            internal string Msg { get; set; }
    
            // 验证是否有效
            internal bool IsValid()
            {
                var v = this as T;
    
                Type type = v.GetType();
    
                PropertyInfo[] propeties = type.GetProperties();
                foreach (PropertyInfo property in propeties)
                {
                    List<Attribute> attributes = property.GetCustomAttributes().ToList();
    
                    var propertyValue = property.GetValue(v);
    
                    Attribute stringlength = attributes.FirstOrDefault(p => p.GetType().IsAssignableFrom(typeof(StringLengthAttribute)));
    
                    if (stringlength == null)
                        continue;
    
                    int length = ((StringLengthAttribute)stringlength).MaximumLength;
    
                    string currentValue = (string)propertyValue;
    
                    if (currentValue.Length > length)
                    {
                        Msg = ((StringLengthAttribute)stringlength).ErrorMessage;
                        return false;
                    }
                }
                return true;
            }
        }

    然后执行结果如图:

    执行结果还行,只不过还需要对基类做扩展,支持针对不同的特性做不同的验证。

    然后我想到了Asp.Net MVC 里面使用的数据模型绑定技术,然后就想能不能使用它的现有的方法,后来就发现了,“System.ComponentModel.DataAnnotations”这个

    具体参考:https://msdn.microsoft.com/en-us/library/system.componentmodel.dataannotations.validator.aspx

    然后针对我的需求写了一个扩展方法,如下.(注意一定要引用:System.ComponentModel.DataAnnotations;

        public static class ExtensionHelper
        {
            /// <summary>
            /// 验证对象是否有效
            /// </summary>
            /// <param name="obj">要验证的对象</param>
            /// <param name="validationResults"></param>
            /// <returns></returns>
            public static bool IsValid(this object obj, Collection<ValidationResult> validationResults)
            {
                return Validator.TryValidateObject(obj, new ValidationContext(obj, null, null), validationResults, true);
            }
    
    
            /// <summary>
            /// 验证对象是否有效
            /// </summary>
            /// <param name="obj">要验证的对象</param>
            /// <returns></returns>
            public static bool IsValid(this object obj)
            {
                return Validator.TryValidateObject(obj, new ValidationContext(obj, null, null), new Collection<ValidationResult>(), true);
            }
        }

    使用方式如下:

     验证相关特性:https://msdn.microsoft.com/en-us/library/system.componentmodel.dataannotations.aspx

    也可以自定义,

      class Program
        {
            static void Main(string[] args)
            {
                DataModel r = new DataModel();
    
    
                r.EmailAddress = "cdaimesdfng1m";
    
    
    
                var v = new Collection<ValidationResult>();
    
                if (r.IsValid(v))
                {
                    Console.WriteLine("1");
                }
                else
                {
                    v.ToList().ForEach(e =>
                    {
                        Console.WriteLine(e.ErrorMessage);
                    });
                }
    
                Console.ReadKey();
            }
        }
    
        public class DataModel
        {
            /// <summary>
            /// 
            /// </summary>
            [Required]
            [StringLength(5, ErrorMessage = "太大")]
            public string Name { get; set; }
    
            /// <summary>
            /// 
            /// </summary>
            [Range(2, 5)]
            public string d { get; set; }
    
            /// <summary>
            /// 
            /// </summary>
            [EmailAddress]
            public string EmailAddress { get; set; }
        }

    Demo下载地址:http://download.csdn.net/detail/u014265946/9330181

    http://tool.nuoeu.com

  • 相关阅读:
    数据结构排序算法之堆排序
    整数划分
    二叉树的递归与非递归
    螺旋数组
    【图的DFS】图的DFS非递归算法
    Docker实战部署应用——Tomcat
    Docker实战部署应用——Redis
    Docker实战部署应用——MySQL5.7
    Docker其他操作:查看内部细节、IP、删除容器
    Docker数据目录相关操作
  • 原文地址:https://www.cnblogs.com/simoncai/p/5022837.html
Copyright © 2011-2022 走看看