2013-04-18 20 views
2

我会重用的OracleConnection对象为多个查询 所以我写了一个简单的类:重用的OracleConnection对象的

public static class DbConnectionsManager 
    { 
     /// <summary> 
     /// 
     /// </summary> 
     private static OracleConnection _dbConnection = null; 


     /// <summary> 
     /// 
     /// </summary> 
     /// <param name="aConnectionString"></param> 
     /// <returns></returns> 
     public static OracleConnection GetDatabaseConnection(string aConnectionString) 
     { 
      try 
      { 
       if (_dbConnection == null) 
       { 
        _dbConnection = new OracleConnection(aConnectionString); 
        _dbConnection.Open(); 
        return _dbConnection; 
       } 

       if (_dbConnection.State == System.Data.ConnectionState.Closed) 
       { 
        _dbConnection.ConnectionString = aConnectionString; 
        _dbConnection.Open(); 
        return _dbConnection; 
       } 

       if (!_dbConnection.ConnectionString.Equals(aConnectionString)) 
       { 
        _dbConnection.Close(); 
        _dbConnection.ConnectionString = aConnectionString; 
        _dbConnection.Open(); 
        return _dbConnection; 
       } 

       return null; 
      } 
      catch (Exception e) 
      { 

       return null; 
      } 
     } 
    } 

这样我就可以使用连接多次:

using (OracleConnection connection = 
      DbConnectionsManager.GetDatabaseConnection(aDbConnectionString)) 
      { 
       OracleCommand command = connection.CreateCommand(); 
       string sql = "SELECT * FROM MYTABLE"; 
       command.CommandText = sql; 

       OracleDataReader reader = command.ExecuteReader(); 
       while (reader.Read()) 
       { 
        string myField = (string)reader["EXAMPLE"]; 
        Console.WriteLine(myField); 
       } 
      } 

当我第一次调用该方法时,一切正常。 如果我记得该方法的静态对象是!= null,但连接结果关闭! 我从不关闭连接!

当您尝试重新打开我有这样的例外

.... 
if (_dbConnection.State == System.Data.ConnectionState.Closed) 
       { 
        _dbConnection.ConnectionString = aConnectionString; 
        _dbConnection.Open(); 
        return _dbConnection; 
       } 
... 

错误

Message = "Cannot access a disposed object.\r\nObject name: 'OracleConnection'." 

回答

3

的错误说,它的处置对象......这意味着你需要删除using (条款,这一条款脱手的连接你连接的对象,你不能在using (之外使用这个对象。这意味着如果您希望在外部使用using (,则需要创建新的物体对象。

你可以通过阅读这篇获得更多的想法:C# Using Statement

1

至于对方的回答解释说,该using子句不是天作之合的东西你想再利用。但是我有同样的想法 - 我仍然希望使用这种模式来自动打开&自动关闭连接。如果这就是你希望做的,那么关键是你正在使用的对象不能是OracleConnection本身,因为你想要重用这个,而使用它会杀死它。你真的只想要一个新的对象,它在创建时打开连接,并关闭Dispose上的连接,仅此而已。这应该做的伎俩(我用它为自己的目的):

internal class OpenedContext : IDisposable 
{ 
    private OracleConnection _connection; 

    public OpenedContext(OracleConnection conn) { 
     _connection = conn; 
     if (_connection.State != System.Data.ConnectionState.Open) _connection.Open();    
    } 

    public void Dispose() { 
     if (_connection.State != System.Data.ConnectionState.Closed) _connection.Close(); 
    } 

} 

,然后在例如,你可以这样做......

  // Early on... 
      OracleConnection _connection = DbConnectionsManager.GetDatabaseConnection(aDbConnectionString); 

      // ... Later on, in various other calls ... 
      using (new OpenedContext(_connection)) 
      { 
       OracleCommand command = _connection.CreateCommand(); 
       string sql = "SELECT * FROM MYTABLE"; 
       command.CommandText = sql; 
       OracleDataReader reader = command.ExecuteReader(); 
       while (reader.Read()) 
       { 
        string myField = (string)reader["EXAMPLE"]; 
        Console.WriteLine(myField); 
       } 
      } 

虽然这是一个愚蠢的方式,我绝对更喜欢设置这样一种模式,以便始终期待未来的编码人员在每次数据库调用时手动“包装”重新打开的重新关闭的&。它更具可读性(或可忽略性),风险较小(如果您非常担心闲置时关闭连接)。