使用通用代表

LCJ*_*LCJ 7 c# generics ado.net

我们知道"Action,Func和Predicate是预定义的通用委托.因此,作为委托,他们可以指向具有指定签名的函数."

我有以下数据访问方案,其中Func<T,R>有助于avoiding a foreach loop调用方法.方法2没有循环.这Func<T,R>有助于避免循环.

泛型委托的其他方案是什么,它可以节省大量的代码行?

参考

  1. 动态编写表达式谓词
  2. 高级C#
  3. C#/.NET Little Wonders:谓词,比较和转换器通用代表
  4. Func vs. Action vs. Predicate
  5. 什么是Func,它是如何以及何时使用的
  6. 如何使用泛型类型参数传入func?

方法1

public class MyCommonDAL
{

    public static IEnumerable<IDataRecord> ExecuteQueryWithTextCommandType(string commandText, List<SqlParameter> commandParameters)
    {
        using (SqlConnection connection = new SqlConnection(connectionString))
        {
            using (SqlCommand command = new SqlCommand())
            {
                command.Connection = connection;
                command.CommandType = CommandType.Text;
                command.CommandText = commandText;
                command.CommandTimeout = 0;
                command.Parameters.AddRange(commandParameters.ToArray());

                connection.Open();
                using (var rdr = command.ExecuteReader())
                {
                    while (rdr.Read())
                    {
                        yield return rdr;
                    }
                    rdr.Close();
                }
            }
        }
    }

}


public class MyLogDAL
{
    public List<LogSeverityType> GetLogSeveritiesFirstApproach(LogSeverityType logSeverityType)
    {


        List<SqlParameter> commandParameters = new List<SqlParameter>()
                                                {
                                                    new SqlParameter {ParameterName = "@CreatedDateTime", 
                                                                      Value = logSeverityType.CreatedDateTime, 
                                                                      SqlDbType = SqlDbType.DateTime}
                                                };


        string commandText = @"SELECT * FROM dbo.LogSeverityType WHERE CreatedDateTime > @CreatedDateTime";
        var results = MyCommonDAL.ExecuteQueryWithTextCommandType(commandText, commandParameters);

        List<LogSeverityType> logSeverities = new List<LogSeverityType>();

 //LOOP
        foreach (IDataRecord rec in results)
        {
            LogSeverityType objLogSeverityType = LogSeverityType.LogSeverityTypeFactory(rec);
            logSeverities.Add(objLogSeverityType);
        }


        return logSeverities;
    }



}
Run Code Online (Sandbox Code Playgroud)

方法2

    public class MyCommonDAL
    {

        public static IEnumerable<T> ExecuteQueryGenericApproach<T>(string commandText, List<SqlParameter> commandParameters, Func<IDataRecord, T> factoryMethod)
        {

            //Action, Func and Predicate are pre-defined Generic delegates.
            //So as delegate they can point to functions with specified signature.

            using (SqlConnection connection = new SqlConnection(connectionString))
            {
                using (SqlCommand command = new SqlCommand())
                {
                    command.Connection = connection;
                    command.CommandType = CommandType.Text;
                    command.CommandText = commandText;
                    command.CommandTimeout = 0;
                    command.Parameters.AddRange(commandParameters.ToArray());

                    connection.Open();
                    using (var rdr = command.ExecuteReader())
                    {
                        while (rdr.Read())
                        {
                            yield return factoryMethod(rdr);
                        }
                        rdr.Close();
                    }
                }
            }
        }


    }


    public class MyLogDAL
    {

        public List<LogSeverityType> GetLogSeveritiesSecondApproach(LogSeverityType logSeverityType)
        {


            List<SqlParameter> commandParameters = new List<SqlParameter>()
                                                    {
                                                        new SqlParameter {ParameterName = "@CreatedDateTime", 
                                                                          Value = logSeverityType.CreatedDateTime, 
                                                                          SqlDbType = SqlDbType.DateTime}
                                                    };


            string commandText = @"SELECT * FROM dbo.LogSeverityType WHERE CreatedDateTime > @CreatedDateTime";
            //var results = MyCommonDAL.ExecuteQueryWithTextCommandType(commandText, commandParameters);

            IEnumerable<LogSeverityType> logSeverities = MyCommonDAL.ExecuteQueryGenericApproach<LogSeverityType>(commandText, commandParameters, LogSeverityType.LogSeverityTypeFactory);

            //foreach (IDataRecord rec in results)
            //{
            //    LogSeverityType objLogSeverityType = LogSeverityType.LogSeverityTypeFactory(rec);
            //    logSeverities.Add(objLogSeverityType);
            //}


            return logSeverities.ToList();
        }


    }
Run Code Online (Sandbox Code Playgroud)

其他代码要求

    public class LogSeverityType
    {
        public int LogSeverityTypeID { get; set; }
        public string Name { get; set; }
        public string Description { get; set; }
        public DateTime CreatedDateTime { get; set; }

        public static LogSeverityType LogSeverityTypeFactory(IDataRecord record)
        {
            return new LogSeverityType
            {
                LogSeverityTypeID = (int)record[0],
                Name = (string) record[1],
                Description = (string)record[2],
                CreatedDateTime = (DateTime) record[3]
            };
        }
    }

        static void Main(string[] args)
        {
            MyLogDAL logDAL = new MyLogDAL();
            LogSeverityType logSeverityType = new LogSeverityType();
            logSeverityType.CreatedDateTime = Convert.ToDateTime("1/1/2000");

            List<LogSeverityType> logSeverities = logDAL.GetLogSeveritiesSecondApproach(logSeverityType);
        }
Run Code Online (Sandbox Code Playgroud)

har*_*ott 1

在解析/查找 XML/HTML 文档中的节点并将值分配给属性时,我使用通用委托。我写了一篇关于它的博客文章,其中展示了重构代码以传递通用委托,以及删除了多少代码。