編集:私にとってうまくいった解決策は、非同期ADO.NETメソッドを使用することでした。BeginExecute...
とEndExecute...
BackgroundWorker
がキャンセルを要求したかどうかを確認しながらクエリを非同期に実行するコードのスニペットを次に示します。この関数は、クエリが最後まで実行された場合は true を返し、キャンセルが実行された場合は false を返します。
BackgroundWorker
コードはのDoWork
関数内のどこかから呼び出す必要があります。
SqlCommand command = new SqlCommand(query, connectionObj);
IAsyncResult result = command.BeginExecuteReader(); // end async execution
// check for user cancellation while result is not complete
while (!result.IsCompleted)
{
if (myBackgroundWorker.CancellationPending)
{
command.Cancel(); // cancel the existing command
try
{
command.EndExecuteReader(result); // cancel async execution
}
catch (SqlException e)
{
// will always enter here due to command.Cancel()
// this is expected
}
return false;
}
Thread.Sleep(100); // sleep so loop doesn't consume all the resources
}
// result is complete, do something with data
using (SqlDataReader reader = command.EndExecuteReader(result))
{
DataTable table = new DataTable();
table.Load(reader);
}
// do something with table
return true;