【问题标题】:ADO.NET DAL and BLLADO.NET DAL 和 BLL
【发布时间】:2015-11-25 18:46:49
【问题描述】:

我有两个类 SqlHelperDishesTypes 用于 DAL 项目

public class SqlHelper
{ 
    public static SqlDataReader ExecuteReader(string procedure, 
        params SqlParameter[] commandParameters) 
    {             
        using (var connection = new SqlConnection(
            ConfigurationManager.ConnectionStrings["DefaultConnection"].ConnectionString))       
        using (var command = new SqlCommand(procedure, _connection)) 
        {                    
            command.CommandType = CommandType.StoredProcedure;
            command.Parameters.AddRange(commandParameters);
            return command.ExecuteReader();                                 
        }    
    }

    public class DishesTypes 
    {
        public static SqlDataReader DishesTypesSelectAll() 
        {
            return SqlHelper.ExecuteReader("DishesTypesSelectAllRows"); //name of procedure
        }
    }

我有 DishedTypes 类,在这样的 BLL 项目中使用

public class DishesTypes
{
    public int DishTypeId { get; set; }
    public string DishType { get; set; }

    public static List<DishesTypes> DishesTypesSelectAll()
    {
        IDataReader dr = DataAccessLayer.DishesTypes.DishesTypesSelectAll();          

        List<DishesTypes> dishesTypesList = new List<DishesTypes>();

        while (dr.Read())
        {
            DishesTypes myDishesTypes = new DishesTypes
            {
                DishTypeId = (int)dr["DishTypeId"],
                DishType = (string)dr["DishType"]
            };
            dishesTypesList.Add(myDishesTypes);
        }
        return dishesTypesList;
    }
}

问题从这里开始while (dr.Read()),原因,到这里的连接已经关闭,需要重新连接如何才能最好地改变粘附层DAL和BLL的类的实现,才能工作?

【问题讨论】:

  • 您不应该在using 语句中添加您返回的内容。它将在调用者控制之外的某个时间被释放或关闭。

标签: c#


【解决方案1】:

如果你想自己动手,像这样更好:

public class DataQuery
{
    private readonly string _connectionString;

    public DataQuery(string connectionString)
    {
        _connectionString = connectionString;
    }

    public IEnumerable<T> GetList<T>(string procedure,
        Func<IDataRecord, T> entityCreator,
        params SqlParameter[] commandParameters
        )
    {
        var result = new List<T>();
        using (var connection = CreateConnection())
        using (var command = CreateCommand(procedure, connection, commandParameters))
        using (var reader = command.ExecuteReader())
        {
            result.Add(entityCreator(reader));
        }
        return result;
    }

    private SqlConnection CreateConnection()
    {
        var connection = new SqlConnection(_connectionString);
        connection.Open();
        return connection;
    }

    private static DbCommand CreateCommand(string procedure, 
        SqlConnection connection, SqlParameter[] commandParameters)
    {
        var command = new SqlCommand(procedure, connection)
        {
            CommandType = CommandType.StoredProcedure
        };
        command.Parameters.AddRange(commandParameters);
        return command;
    }
}

你会这样称呼:

var connectionString = ConfigurationManager.ConnectionStrings["DefaultConnection"]
    .ConnectionString;

var query = new DataQuery(connectionString);
Func<IDataRecord, DishesTypes> creator = dr => 
    new DishesTypes
    {
        DishTypeId = (int)dr["DishTypeId"],
        DishType = (string)dr["DishType"]
    };

var results = query.GetList("DishesTypesSelectAllRows", creator);

否则,我建议您查看Dapper

Dapper 可以让你简单地做:

var results = connection.Query<DishesTypes>("DishesTypesSelectAllRows", 
    commandType: CommandType.StoredProcedure);

【讨论】:

    【解决方案2】:

    首先,您的using 语句正在关闭您的连接,因此您不能期望返回可用的IDataReader。其次,您的连接永远不会打开,因此无论如何您都不会得到结果。话虽如此,如果您的数据集总是足够小以适合内存,您可以使用类似于我在下面所做的事情。这对您的代码的影响应该很小。

        public class SqlHelper
        {
            public static IDataReader ExecuteReader(string procedure, params SqlParameter[] commandParameters)
            {
                using (var connection = new SqlConnection(ConfigurationManager.ConnectionStrings["DefaultConnection"].ConnectionString))
                {
                    connection.Open();
                    using (var command = new SqlCommand(procedure, connection))
                    {
                        command.CommandType = CommandType.StoredProcedure;
                        command.Parameters.AddRange(commandParameters);
                        DataTable dt = new DataTable();
                        using (SqlDataAdapter da = new SqlDataAdapter(command))
                            da.Fill(dt);
                        return dt.CreateDataReader();
                    }
                }
            }
        }
    
        public class DishesTypes
        {
            public static IDataReader DishesTypesSelectAll()
            {
                return SqlHelper.ExecuteReader("DishesTypesSelectAllRows");//name of procedure
            }
    
        }
    

    【讨论】:

      猜你喜欢
      • 2010-10-01
      • 2011-01-23
      • 2013-09-24
      • 2011-04-03
      • 2011-04-26
      • 2013-05-31
      • 2013-02-06
      • 2010-09-30
      • 2010-12-24
      相关资源
      最近更新 更多