通用数据读取器导致内存泄漏

问题描述 投票:1回答:1

我在读取sql语句时创建了一个通用方法,但是每当执行选择查询并在读取时使用时,都会发生内存泄漏。

示例查询:

    public CMItemPackagingType GetItemPackagingType(int itemID)
    {  
        try
        {               
            List<CommandParameter> param = new List<CommandParameter>();
            StringBuilder sb = new StringBuilder();
            using (BaseConnection db = new BaseConnection())
            {
                sb.Append("SELECT RATIO, PACKAGING_TYPE_CODE FROM ITEM_PACKAGING_TYPE WHERE ROUND_UP = 0.01 AND ITEM_ID = @itemID");

                param.Add(new CommandParameter("@itemID", itemID));
                using (var rs = db.ExecSQL(sb.ToString(), param.ToArray()))
                {
                    CMItemPackagingType cmItemInfo = new CMItemPackagingType();

                    while (rs.Read())
                    {
                        CMItemPackagingType list = new CMItemPackagingType();
                        if (!rs.IsDBNull(0))
                            list.Ratio = Convert.ToInt32(rs.GetValue(0));
                        if (!rs.IsDBNull(1))
                            list.PackagingTypeCode = rs.GetValue(1).ToString();

                        cmItemInfo.ItemPackagingTypeList.Add(list);
                    }
                    return cmItemInfo;
                }        
            }       
        }
        catch (Exception ex)
        {                
            GlobalFramework.HandleException(ex);
        }
        return null;
    }       

通用阅读器:

public DbDataReader ExecSQL(string sqlStmt, CommandParameter[] param)
    {

            List<MySqlParameter> p = ParameterMySql(param);
            _mySqlConn = new MySqlConnection(szConnect);
            if (_mySqlConn.State == ConnectionState.Open)
            {
                _mySqlConn.Close();
            }
            _mySqlConn.Open();
            _mySqlComm = new MySqlCommand(sqlStmt, _mySqlConn);
            _mySqlComm.Parameters.AddRange(p.ToArray());
            MySqlDataReader reader = _mySqlComm.ExecuteReader();

            return reader;

    }
memory memory-leaks sqldatareader
1个回答
0
投票

我假设BaseConnection是SqlConnection的包装,而_mySqlConn是BaseConnection的实例。我怀疑问题在于您正在ExecSQL中打开和关闭连接,同时在BaseConnection周围有一个using语句会造成此泄漏。我会通过正确放置using语句来重构您的代码,以确保正确处置对象和释放资源。

示例

        var query = "YOUR QUERY";

        using (var connection = new SqlConnection("YOUR CONNECTION STRING"))
        {
            using (var command = new SqlCommand(query, connection))
            {
                await connection.OpenAsync();

                using (var reader = await command.ExecuteReaderAsync())
                {
                    if (reader != null)
                    {
                        while (await reader.ReadAsync())
                        {
                            // your logic
                        }
                    }
                } // reader closed and disposed up here
            } // command disposed here
        } //connection closed and disposed here
    }

也请注意我如何使用ADO.NET方法的异步版本。异步命令对于实现规模,吞吐量和延迟至关重要。

我建议您在尝试开发通用数据读取器并亲自编写所有样板ADO.NET代码时使用Dapper

最新问题
© www.soinside.com 2019 - 2025. All rights reserved.