Hi All,
Lately I explore about multi threading,because there is a urgent need to implement this feature.I came up with a case of multi threading cancellation. There is two kind of multi threading we have.
1. threading in the program itself. ex.
Private Sub Worker_DoWork(ByVal sender As Object, ByVal e As System.ComponentModel.DoWorkEventArgs) Handles Worker.DoWork
Dim intI As Integer
Dim intJ As Integer
Dim intK As Integer
Dim counter As Integer
For intI = 1 To 20
For intJ = 1 To 20
For intK = 1 To 20
counter = counter + 1
'DO SOMETHING HERE
Next
Worker.ReportProgress(counter / 8000 * 100)
Next
Next
End Sub
2. threading that branch to Database. ex.
Private Sub Worker_DoWork(ByVal sender As Object, ByVal e As System.ComponentModel.DoWorkEventArgs) Handles Worker.DoWork
objDataTable=<Query to a very huge database)
End Sub
We want a button to cancel the thread. I read we can use cancelasync and the check cancellationpending flag in the doWork. But where should put this thing in the both case
Please help.
Thank you very much.
Regards,
Freddy halim

Multithreading cancellation Methode
RookieDBA
Hi Freddy
I am not familiar with the background worker class, but you seem to be suggesting that the worker thread is tied up in the database and therefore not actually 'running'. If this is the case, I'd recommend you control the worker thread yourself and terminate it manually.
You can spawn a worker thread yourself, and you can abort the thread manually which will raise an exception in the worker method (ThreadAbortException) that you can trap. Note that the operation of closing a thread is not inherently synchronous, hence the call to the Join method.
It may not be the exact pattern you need but hopefully it is something that you may be able to consider/tweak.
Private wt As Threading.Thread Private syncRoot As New Object Sub StartWork() SyncLock syncRootwt =
New Threading.Thread(AddressOf Me.DoWork)wt.IsBackground =
Truewt.Start()
End SyncLock End Sub Sub StopIfWorking() SyncLock syncRoot If wt IsNot Nothing Thenwt.Abort() : Threading.Thread.CurrentThread.Join(timeout)
wt = Nothing
End If End SyncLock End Sub Sub DoWork() Try Catch ex As Threading.ThreadAbortException End Try End SubRichard
karthik asok
You could put an IF statement where it could check fairly often whether there's a cancelation pending. Maybe something like:
I haven't played with connecting to a database, but my guess is that you could do something similar:
Your main thread that started the background worker can trigger off the cancel button click to generate the BackgroundWorker.CancelAsync() that sets the CancellationPending flag to true.
Sundararajan
rKarthik
Yeah, I try your solution it is work for my first case.
But still i got problem report to progress bar since the thread is not interference with other ( thread safe).Here is my problem.
Private Sub DoWork1()
Try
Dim objConnection As OleDbConnection
Dim objCommand As OleDbCommand
Dim intI As Integer
Dim intJ As Integer
Dim intK As Integer
Dim counter As Integer
objConnection = New OleDbConnection(vConnString)
objConnection.Open()
objCommand = objConnection.CreateCommand
For intI = 1 To 20
For intJ = 1 To 20
For intK = 1 To 20
counter = counter + 1
Try
objCommand.CommandText = "INSERT INTO tblTest(col1,col2,col3) VALUES " & _
"('" & intI & "','" & intJ & "','" & intK & "')"
objCommand.ExecuteNonQuery()
Catch ex As Exception
MessageBox.Show("Thread is closing")
End Try
Next
ProgressBar1.Value = counter / 8000 * 100 <==== this is my error
Next
Next
objConnection.Close()
Catch ex As Threading.ThreadAbortException
MessageBox.Show(ex.ToString)
End Try
End Sub
Are there any solution
Still the second case has no solution.If the thread query to a huge DB.How to cancel the thread.
Are there any suggestion
Dears,
Freddy
Glyn Darkin
Hi Freddy
I'm not 100% sure what you are asking. Hopefully, some of the following will prove relevant and make sense to you.
DoWork1 is presumably running on a background thread. This means that it cannot interact directly with the progress bar as it is not the thread that created that control. What you need to do, is update the progress bar through another method and call that method via a delegate that is passed to the Invoke method of the progress control. Something like this should help ....
private delegate sub updateprogressbardelegate (byval value as double)
private sub updateprogressbar(byval value as double)
if progressbar.invokerequired then
progressbar.invoke(new updateprogressbardelegate(addressof updateprogressbar), value)
else : progressbar.value = value
end if
end sub
Simply replace the call to the setter ProgressBar1.Value = XXX to call the update progress bar method instead.
If the above is not what you were looking for, please let me know and I will try to help.
Richard
Kapoulkine Arseny