Не работает асинхронная отмена фонового рабочего процесса

#.net #vb.net #backgroundworker

#.net #vb.net #фоновый рабочий

Вопрос:

Логика программы

Я запускаю фоновый рабочий процесс для чтения и записи файлов. Для проверки того, нажата ли кнопка отмены, я создал метод с именем «check_bgWorkerCancelled()», и предполагается, что он обрабатывает все события, если ожидаемая отмена.

Проблема

Когда я нажимаю кнопку отмены, рабочий продолжает работать. Когда я нажимаю кнопку «Пуск», старый процесс продолжает выполняться.

Код: Для проверки отмены

 ' Method: To check is cancellation is pending
    Private Sub check_bgWorkerCancelled()
        ' check if cancellation is pending
        If bgWorker_Scanner.CancellationPending = True Then
            ' background worker cancel asynchronous operating
            If bgWorker_Scanner.IsBusy Then
                Try 'try to
                    ' cancel the threads
                    bgWorker_Scanner.CancelAsync()
                    ' dispose the background worker
                    bgWorker_Scanner.Dispose()
                Catch ex As Exception 'if exception
                    ' invoke error
                    utils.invoke_msg(3, "Worker Error", ex.Message.ToString)
                    Me.Close() 'close form
                End Try
            End If
            isScanning = False 'set scanning to false
            Try
                ' invoke to bypass illegal cross threading UI update
                BeginInvoke(CType(Sub()
                                      progressBar1.Value = 0
                                      txtStatus.Text = "Cancelled"
                                      txtCalmDown.Text = ""
                                      btnToggleScan.Image = Image.FromFile(Application.StartupPath amp; "/res/malware_scanner/rocket.png")
                                  End Sub, MethodInvoker))
            Catch ex As Exception : End Try
        Else
            Exit Sub
        End If
    End Sub
  

Пробованные решения

Я пробовал следующие решения, но ни одно из них не сработало:

Пытался проверить отмену внутри события DoWork

 Private Sub bgWorker_Scanner_DoWork(sender As Object, e As System.ComponentModel.DoWorkEventArgs) Handles bgWorker_Scanner.DoWork
    If bgWorker_Scanner.CancellationPending = True Then
        e.CancelAsync()
        bgWorker_Scanner.dispose()
    End If
End Sub
  

Пытался проверить отмену и собрать мусор

 Private Sub bgWorker_Scanner_DoWork(sender As Object, e As System.ComponentModel.DoWorkEventArgs) Handles bgWorker_Scanner.DoWork
    If bgWorker_Scanner.CancellationPending = True Then
        e.CancelAsync()
        bgWorker_Scanner.dispose()
        GC.Collect()
    End If
End Sub
  

Пытался выполнить вышеуказанное внутри инструкций Try-Catch

 Private Sub bgWorker_Scanner_DoWork(sender As Object, e As System.ComponentModel.DoWorkEventArgs) Handles bgWorker_Scanner.DoWork
    If bgWorker_Scanner.CancellationPending = True Then
        If bgWorker_Scanner.IsBusy Then
            Try
                e.CancelAsync()
                bgWorker_Scanner.dispose()
                GC.Collect()
            Catch ex As Exception
                MsgBox(ex.Message.ToString)
        End If
    End If
End Sub
  

Отладочный образ

Есть ли какой-либо способ завершить фоновый рабочий процесс без необходимости полного закрытия формы? Приветствуется любая помощь.

Комментарии:

1. Если bgWorker_Scanner.CancellationPending Then 'Do something e.Cancel = True End If . Call [BackGroundWorker].CancelAsync() извне .

2. @Jimi Я вызвал CancelAsync() с помощью кнопки. Теперь, похоже, по какой-то причине возникла другая проблема.. Есть значок курсора ожидания, и кнопка по умолчанию отключена. Я не устанавливал это, но я предполагаю, что Windows делает это автоматически.. Я не могу получить доступ к кнопке, пока не будет завершена вся операция:'(

3. Вы явно не знаете, как правильно использовать BackgroundWorker . Перейдите сюда , чтобы узнать. Сообщение # 19 содержит пример отмены.

4. Я надеюсь, вы все еще не пытаетесь избавиться от BackgroundWorker внутри DoWork или вызываете GC.Collect() . Если вы находитесь в цикле во время CancelAsync вызова, выйдите из цикла (после e.Cancel = True ).