C# と VB.NET の質問掲示板

わんくま同盟

ASP.NET、C++/CLI、Java 何でもどうぞ

C# と VB.NET の入門サイト

■102558 / 1階層)  (追質)時間のかかる処理の進行の表示
□投稿者/ 魔界の仮面弁士 (3710回)-(2023/11/17(Fri) 20:56:06)
2023/11/18(Sat) 11:04:44 編集(投稿者)

# パラメーター指定をミスっていたので修正
# そして 6 分差で被っちゃいました…(手順が違うけれど、ひとまとめに渡すという方針では同じ)

No102556 (焼いも さん) に返信
> Do While Not sr.EndOfStream
>   Dim dt As String = sr.ReadLine '1行全てを読み取る
>   Await Task.Run(

依頼者「No1 を処理してください」
作業者「了解…(長い処理)…終わりました」
依頼者「(ProgressBar を +1)」
依頼者「No2 を処理してください」
作業者「了解…(長い処理)…終わりました」
依頼者「(ProgressBar を +1)」


これじゃ遅いですよ。
細切れにして何度も依頼しなおさないで、
全部まとめて、1 回だけ依頼しましょう。


依頼者「これらのデータを順に処理して、終わったものから随時報告してください」


進捗通知のための IProgress(Of T) を使ってみた例。


Sub 画面表示更新処理(hoge As 任意の型)
 'ここは呼び出し元のスレッドで動くので、ProgressBar 等を操作しても構わない
 '引数 hoge から進捗状況を受け取り、Label や ProgressBar 等に反映
End Sub

'今回の本題は IProgress
'それ以外の引数は不要なら省いてもよいし、別の引数を追加してもよい
Function 時間のかかる処理本体部(argument As 処理させたいデータ, p As IProgress(Of 任意の型), cancelToken As CancellationToken) As Boolean
 'ここはワーカースレッドで動くので、画面操作は禁止
 For Each foo In argument
  If cancelToken.IsCancellationRequested Then 'キャンセル依頼あり
   Debug.WriteLine("キャンセル処理のための処理")
   Return False '中断
  End If

  Debug.WriteLine("長い処理")
  Thread.Sleep(1000)

  '引数 p を通じて進捗状況を記録
  p.Report( 進捗状況データ )

 Next
 Return True '全件処理完了
End Function

Async Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
 Button1.Enabled = False '多重呼び出しされないようにブロック

 '進捗報告のための IProgress(Of T) 実装を用意
 Dim p As New Progress(Of 任意の型)(AddressOf 画面表示更新処理)

 '中断依頼を受け付けるためのトークンを用意(今回は使ってない)
 Me.cancelTokensource = New CancellationTokenSource()
 Dim cToken = Me.cancelTokenSource.Token

 '時間のかかる処理
 Dim completed = Await Task.Run(Function() 時間のかかる処理本体部(作業依頼データ, p, cToken))
 If completed Then
  Label1.Text = "完了"
 Else
  Label1.Text = "中断"
 End If

 Button1.Enabled = True
End Sub
Private cancelTokenSource As CancellationTokenSource
Private Sub Button2_Click(sender As Object, e As EventArgs) Handles Button2.Click
 '中断依頼
 cancelTokenSource?.Cancel()
End Sub



なお、順次処理である必要が無い場合は Parallel.For や Parallel.ForEach などを使う手法もあります。
(データを幾つかに分割し、複数の作業者に同時に依頼して並列処理させるイメージ)
編集キー/

前の記事(元になった記事) 次の記事(この記事の返信)
←(追質)時間のかかる処理の進行の表示 /焼いも →Re[2]: (追質)時間のかかる処理の進行の表示 /焼いも
→Re[2]: (追質)時間のかかる処理の進行の表示 /とっちゃん
 
上記関連ツリー

(追質)時間のかかる処理の進行の表示 / 焼いも (23/11/17(Fri) 18:27) #102556
Re[1]: (追質)時間のかかる処理の進行の表示 / とっちゃん (23/11/17(Fri) 20:50) #102557
│├ Re[2]: (追質)時間のかかる処理の進行の表示 / 焼いも (23/11/18(Sat) 10:24) #102559
│└ Re[2]: (追質)時間のかかる処理の進行の表示 / WebSurfer (23/11/18(Sat) 15:04) #102562
(追質)時間のかかる処理の進行の表示 / 魔界の仮面弁士 (23/11/17(Fri) 20:56) #102558 ←Now
  ├ Re[2]: (追質)時間のかかる処理の進行の表示 / 焼いも (23/11/18(Sat) 10:40) #102560
  │└ Re[3]: (追質)時間のかかる処理の進行の表示 / WebSurfer (23/11/18(Sat) 12:05) #102561
  │  └ Re[4]: (追質)時間のかかる処理の進行の表示 / 焼いも (23/11/18(Sat) 15:29) #102563
  │    └ Re[5]: (追質)時間のかかる処理の進行の表示 / WebSurfer (23/11/18(Sat) 15:52) #102564
  │      └ Re[6]: (追質)時間のかかる処理の進行の表示 / 焼いも (23/11/18(Sat) 20:07) #102567
  │        └ Re[7]: (追質)時間のかかる処理の進行の表示 / WebSurfer (23/11/19(Sun) 10:22) #102574
  │          └ Re[8]: (追質)時間のかかる処理の進行の表示 / 焼いも (23/11/20(Mon) 00:00) #102578
  │            └ Re[9]: (追質)時間のかかる処理の進行の表示 / WebSurfer (23/11/20(Mon) 09:06) #102582
  │              └ Re[10]: (追質)時間のかかる処理の進行の表示 / 焼いも (23/11/20(Mon) 15:45) #102583
  │                └ Re[11]: (追質)時間のかかる処理の進行の表示 / WebSurfer (23/11/20(Mon) 17:13) #102585
  │                  └ Re[12]: (追質)時間のかかる処理の進行の表示 / 焼いも (23/11/21(Tue) 00:59) #102588
  └ Re[2]: (追質)時間のかかる処理の進行の表示 / とっちゃん (23/11/19(Sun) 02:11) #102572
    └ Re[3]: (追質)時間のかかる処理の進行の表示 / 焼いも (23/11/20(Mon) 00:07) #102579
      └ Re[4]: (追質)時間のかかる処理の進行の表示 / とっちゃん (23/11/20(Mon) 01:48) #102581
        └ Re[5]: (追質)時間のかかる処理の進行の表示 / 焼いも (23/11/20(Mon) 15:47) #102584
          └ Re[6]: (追質)時間のかかる処理の進行の表示 / とっちゃん (23/11/20(Mon) 17:37) #102586
            └ Re[7]: (追質)時間のかかる処理の進行の表示 / 焼いも (23/11/21(Tue) 00:53) #102587 解決済み
              └ Re[8]: (追質)時間のかかる処理の進行の表示 / WebSurfer (23/11/21(Tue) 18:07) #102589 解決済み

上記ツリーを一括表示 / 上記ツリーをトピック表示
 
上記の記事へ返信