asp.NetでSqlDataReader使用時にデータベース接続を閉じる問題
たとえば、データベースの操作を1つのクラスにカプセル化しますが、SqlDataReaderは読み取りが完了したときにのみデータベースを閉じることができ、クラスではライブラリ接続を閉じることはできません.関数で閉じる、関数で閉じると「リーダーが閉じるときにReadの試行が無効」というメッセージが表示されます.
この点はマイクロソフトが当然考えた.方法dr=Cmd.ExecuteReader(CommandBehavior.CloseConnection);,MSDNでCommandBehavior.CloseConnectionは、「このコマンドを実行すると、関連付けられたDataReaderオブジェクトを閉じると、関連付けられたConnectionオブジェクトも閉じます」と説明しています.
でも....、次の質問を参照してください.
関数で操作を実行してDataReaderに戻り、外でデータを読み出し、読み取りが完了したら外部でDataReaderを閉じると、関数のConnetionは自動的に閉じますか?
例:
私はすべてのデータベースに対する操作を1つのクラスにカプセル化して、プログラムを書く時直接このクラスのある関数を呼び出して結果を返します!(私たちはネットを勉強しています.weareleran.net)
DataReader ,
public SqlDataReader GetReader(string SQL)
{
SqlConnection Conn;
Conn = new SqlConnection(strConn);
Conn.Open();
SqlCommand Cmd ;
Cmd = CreateCmd(SQL, Conn);
SqlDataReader dr;
try
{
dr = Cmd.ExecuteReader(CommandBehavior.CloseConnection);
}
catch
{
throw new Exception(SQL);
}
Cmd.Dispose();
return dr;
}
プログラムが必要な時、私は直接SQL文を構築して、この関数を呼び出せばいいです.以下のようにします.
string sql="select * form student";
SqlDataReader dr = mydate.GetReader(sql);// GetReader , SqlDataReader
if(dr.Read())
{
......... , .....
}
dr.Close();// , DataReader
私はこのように書くのは基本的に大丈夫で、正常にデータを読み出すことができますが、私が今心配している問題の一つはConnectionオブジェクトの閉じる問題です.関数に確立されたConnectionオブジェクトなので、外部で閉じることはできません.また、関数で閉じることはできません.関数で閉じると「リーダーが閉じるときのReadの試みは無効」というメッセージが表示されますが、私は関数でこの行を使いました.dr=Cmdです.ExecuteReader(CommandBehavior.CloseConnection);,MSDNでCommandBehavior.CloseConnectionは、「このコマンドを実行すると、関連付けられたDataReaderオブジェクトを閉じると、関連付けられたConnectionオブジェクトも閉じます」と説明しています.つまり、DataReaderをオフにすると、関連するConnectionが自動的にオフになります.私もテストしました.テストコードは以下の通りです.
string strConn = ConfigurationSettings.AppSettings["SqlDatabase"];
SqlConnection cn=new SqlConnection(strConn);
cn.Open();
string sql="select * form student";
SqlCommand cm=new SqlCommand(sql,cn);
SqlDataReader dr=cm.ExecuteReader(CommandBehavior.CloseConnection);
SqlDataReader dr = mydate.RunProcGetReader(sql);
if(dr.Read())
{
.......
}
dr.Close();// DataReader
Response.Write(cn.State);// Connetion
その結果、このセクションを実行し、出力:Closed、Connetionが自動的に閉じたことがわかります!しかし、私が上で述べたように、私のCoonectionは関数が確立されていて、関数の中で操作を実行してDataReaderに戻り、外でデータを読み出して、読み取りが終わったら外部でDataReaderを閉じて、このように関数の中のConnetionは自動的に閉じますか?
私はすべてのデータベースに対する操作を1つのクラスにカプセル化して、プログラムを書く時直接このクラスのある関数を呼び出して結果を返します!次に、DataReaderオブジェクトを返す汎用クラスを示します.
public SqlDataReader GetReader(string SQL)
{
SqlConnection Conn;
Conn = new SqlConnection(strConn);
Conn.Open();
SqlCommand Cmd ;
Cmd = CreateCmd(SQL, Conn);
SqlDataReader dr;
try
{
dr = Cmd.ExecuteReader(CommandBehavior.CloseConnection);
}
catch
{
throw new Exception(SQL);
}
Cmd.Dispose();
return dr;
}
プログラムが必要なときにSQL文を直接構築し、string sql=「select*form student」のようにこの関数を呼び出すことができます. SqlDataReader dr = mydate.GetReader(sql);//データベース操作汎用クラスのGetReader関数を呼び出し、SqlDataReader if(dr.Read(){......データを読み出し、ページコントロールに値を付与する..... } dr.Close();//操作が终わって、DataReaderを闭じます私はこのような书き込みによって基本的にすでに问题がなくて、正常にデータを読み出すことができて、しかし私が今心配している1つの问题はConnectionオブジェクトの闭じる问题で、関数の中で创立するConnectionオブジェクトなので、外部でそれを闭じることができなくて、また関数の中で闭じることができません関数で閉じると「リーダーが閉じるときのReadの試みは無効」というメッセージが表示されますが、私は関数でこの行を使いました.dr=Cmdです.ExecuteReader(CommandBehavior.CloseConnection);,MSDNでCommandBehavior.CloseConnectionは、「このコマンドを実行すると、関連付けられたDataReaderオブジェクトを閉じると、関連付けられたConnectionオブジェクトも閉じます」と説明しています.つまり、DataReaderをオフにすると、関連するConnectionが自動的にオフになります.私もテストしました.テストコードは以下の通りです.
string strConn = ConfigurationSettings.AppSettings["SqlDatabase"];
SqlConnection cn=new SqlConnection(strConn);
cn.Open();
string sql="select * form student";
SqlCommand cm=new SqlCommand(sql,cn);
SqlDataReader dr=cm.ExecuteReader(CommandBehavior.CloseConnection);
SqlDataReader dr = mydate.RunProcGetReader(sql);
if(dr.Read())
{
.......
}
dr.Close();// DataReader
Response.Write(cn.State);// Connetion
その結果、このセクションを実行し、出力:Closed、Connetionが自動的に閉じたことがわかります!しかし、私が上述したように、私のCoonectionは関数が確立されているので、関数で操作を実行してDataReaderに戻り、外でデータを読み出し、読み取りが終わったら外部でDataReaderを閉じると、関数のConnetionは自動的に閉じますか?
自分でテストをしました:(私たちはネットを勉強しました-www.wearelearn.net)
public SqlConnection conn;
protected void Page_Load(object sender, EventArgs e)
{
conn = new SqlConnection(DAL.SQLHelper.conn_String);
show();
}
//
protected static SqlDataReader reDatareader(SqlConnection conn)
{
SqlCommand cmd = new SqlCommand("select top 10 * from article ", conn );
conn.Open();
SqlDataReader dr = cmd.ExecuteReader(CommandBehavior.CloseConnection);
return dr;
}
//
protected SqlDataReader redr()
{
SqlDataReader dr = reDatareader(conn);
return dr;
}
// , 3 。
protected void show()
{
SqlDataReader dr = redr();
if (dr.HasRows)
{
while (dr.Read())
{
}
Response.Write(conn.State.ToString());
dr.Dispose();
Response.Write(conn.State.ToString());
}
}
結果はOpenClosedを出力して、ほほほ、結果は閉じることができます.
ソース:
http://hi.baidu.com/westfruit/blog/item/6ed56f1911927b4f43a9ad87.html