C#のCancellationTokenを使ったキャンセル処理を完全ガイド!非同期処理を安全に止める方法
生徒
「C#で時間のかかる処理を途中で止めることってできますか?」
先生
「できますよ。C#ではCancellationTokenを使うと、安全に処理を中断できます。」
生徒
「強制的に止めるんじゃなくて、安全に、というのはどういう意味ですか?」
先生
「それでは、キャンセル処理の考え方から順番に見ていきましょう。」
1. C#のキャンセル処理とは?
C#のキャンセル処理とは、実行中の処理を途中でやめたいときに使う仕組みです。 たとえば、ダウンロード中に「やっぱりやめたい」と思ったり、ボタンを押して長い処理を止めたい場面があります。
パソコン初心者の方は、電子レンジを想像してください。温め中に「止める」ボタンを押すと、安全に動作が止まります。 C#でも同じように、無理やり止めず、自分から止まる合図を送る方法が用意されています。
非同期プログラミングでは、この仕組みが特に重要です。強制終了はエラーや不具合の原因になるため、 CancellationTokenを使った安全なキャンセル処理が推奨されています。
2. CancellationTokenとCancellationTokenSourceの基本
キャンセル処理には、CancellationTokenとCancellationTokenSourceという
2つのクラスが登場します。
CancellationTokenSourceは「キャンセルしていいよ」という合図を出す人です。 CancellationTokenは、その合図を受け取るためのチケットのような存在です。
料理に例えると、CancellationTokenSourceが「もう調理をやめて」と言い、 CancellationTokenがそれを聞いてコンロの火を弱める役割になります。
CancellationTokenSource cts = new CancellationTokenSource();
CancellationToken token = cts.Token;
3. 非同期メソッドでキャンセルを受け取る
C#の非同期メソッドでは、asyncとawaitを使います。
キャンセル処理を行う場合、引数としてCancellationTokenを受け取ります。
処理の途中で「キャンセルされたかどうか」を確認し、自分から処理を終えるのがポイントです。
async Task LongTaskAsync(CancellationToken token)
{
for (int i = 0; i < 5; i++)
{
token.ThrowIfCancellationRequested();
await Task.Delay(1000);
Console.WriteLine("処理中...");
}
}
4. キャンセルを実行する方法
実際に処理を止めるには、CancellationTokenSourceのCancelメソッドを呼びます。
これは「もう止まっていいよ」と伝える操作です。
CancellationTokenSource cts = new CancellationTokenSource();
Task task = LongTaskAsync(cts.Token);
Thread.Sleep(2000);
cts.Cancel();
このようにすると、処理は次にキャンセル確認を行ったタイミングで終了します。 強制終了ではないため、プログラムが不安定になりにくいのが特徴です。
5. OperationCanceledExceptionとは?
ThrowIfCancellationRequestedが呼ばれると、
OperationCanceledExceptionという例外が発生します。
例外と聞くと難しく感じますが、「処理を中断した」という合図のようなものです。 エラーではなく、想定された動きなので安心してください。
try
{
await LongTaskAsync(cts.Token);
}
catch (OperationCanceledException)
{
Console.WriteLine("キャンセルされました。");
}
6. CancellationTokenを使うメリット
CancellationTokenを使う最大のメリットは、安全で読みやすいコードになることです。 処理を止めるタイミングを自分で決められるため、途中のデータが壊れる心配がありません。
また、非同期処理やTaskと組み合わせることで、実際のアプリケーション開発でもよく使われています。 ダウンロード処理、ファイル操作、通信処理など、幅広い場面で活躍します。
C#の非同期プログラミングを学ぶ上で、CancellationTokenは避けて通れない重要な要素です。