threading tasks

securonic

Active member
Joined
Aug 29, 2010
Messages
34
Location
Midlands Uk
Programming Experience
Beginner
hi everyone.

i am trying to get my head around how the threading within vb actually works. am i of the understanding that every time you create an event, through a button control for instance, that this infact creates a seperate process which will run independantly to another. say for instance you had two buttons on a form and each contained code which took 5 seconds to execute. if i were to click one button into action and then the other with a second, would the two processes run alongside one another or would i have to wait for the first code to execute before the second button could be executed?

thanks for reading and hope to get some insight.

cheers
 
events don't inherently create new threads (though some events have the potential to... and if you write your own event you definitely have the ability to).

events will fire in the order the delegates were added to the event. One at a time, one after the other, and if any one of the handlers is slow, then it will slow down like that.

Furthermore the events will occur on the thread they were fired from. So a CLICK event is going to be on the main ui thread, because it's an ui event. Let's take for example:

VB.NET:
    Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
        System.Threading.Thread.Sleep(9000)
    End Sub

If I click Button1, then the form this button is on will become unresponsive for 9 seconds (I put the thread the click event happened on to sleep, that being the ui thread, and the code for dragging windows occurs on the ui thread as well).




Do note though that I said the event occurs on the thread it was fired from. And click events are almost always fired from the ui thread because that's where the code that handles mouse clicks tends to be ran by windows forms. BUT there is the protected OnClick event defined for all Controls that can be called by custom code... and if this is so, the Click event (or any event you handle that has this occur) will be on that thread.
 
lordofduct said:
event occurs on the thread it was fired from
Events are raised, not fired, thus RaiseEvent statement. This is actually mentioned in MS guidelines, and they really mean it :)
Do use the raise terminology for events rather than fire or trigger.
 
oh no, differing nomenclature...

next we'll have the paradigm vs programming debaucle.



Sorry but Microsoft and .Net did not invent the event driven system. So changing my informal vocabulary (it's not like I was writing published word here) to meet some ridiculous "guideline" that just slilghtly differentiates their technology from others is well... annoying and condescending on their part.
 
Informal nomenclature is a good way to cause confusion. In post #2 above, the term "event" is used to describe events, event handlers and methods, when each is a different thing.

As suggested, events are raised using using the RaiseEvent statement. Events can't create threads. Generally speaking, an event will be raised via the RaiseEvent statement in a method named after the event, e.g. the OnClick method of a control will raise the Click event. The method that raises the event is being executed on a particular thread so the event is raised on that thread, which means that all the handlers for that event are executed on that thread. As suggested, the OnClick method of a control executes on the UI thread, so the Click event is raised on the UI thread, so the Click event handler is executed on the UI thread. By default, the FileSystemWatcher and System.Timers.Timer classes raise their events on a thread pool thread, so the handlers for those events will be raised on those same thread pool threads. If you set the SynchronizingObject property of a FileSystemWatcher or Timer though, it will raise its events on the thread that owns that object.
 
i'll be honest here and i really do sincerely appreciate your help but i really am lost now. looks like i have a lot to look into regarding this because not much of what has been said is at all for laymens.... thinking about what i have tried to understand, could i assume that an event raised will place that event in a queue to exacute and execute only once the the UI thread has completed the prior event? such as the filesystem watcher might queue changing states within a folder? not entirely sure what a thread pool is mind, so still in the dark on that. what is the difference between a UI thread and a pool thread or any other for that matter?? i suppose i could surmise that pool threading would mean a shared thread but not really sure what that would mean for the code even so. can you create a thread ouside a pool or a UI?
 
ok, been doing some more reading here. seems i have a 'background worker' at my disposal. seems pretty straight forward but still need a few points ironing out. if i used the the background worker in such a way that i call'd sub routines from within it. would those routines be processed under that new thread?
ie,

Private Sub BackgroundWorker1_DoWork(ByVal sender As System.Object, ByVal e As System.ComponentModel.DoWorkEventArgs) Handles BackgroundWorker1.DoWork

if textbox1.text = "" then
call sub1()
call sub2()
end if

End Sub
 
If you call a method M1 from within a method M2 then M2 executes on the same thread that M1 was executing on unless you explicitly start a new thread or marshal the method call to some other existing thread. The BackgroundWorker is intended to be a simple way to implement multi-threading. You don't have to create any threads and you don't have to use delegation to update the UI. All you have to do is call methods and handle events, which is something that everyone has done many times. You call the RunWorkerAsync on the UI thread and the BackgroundWorker raises its DoWork event on a thread pool thread. You handle the DoWork event and, because the event is raised on a background thread, your event handler is executed on that background thread.

If you need to update the UI you cannot do it in the DoWork event handler or any method called from the DoWork event handler, because they are all executed on the same background thread. To update the UI during the background operation you call the ReportProgress method and handle the ProgressChanged event. Because the ProgressChanged event is raised on the UI thread, your event handler is executed on the UI thread, so you can update the UI. If you need to update the UI when the background operation is complete, you handle the RunWorkerCompleted event, which is also raised on the UI thread.
 
Informal nomenclature is a good way to cause confusion. In post #2 above, the term "event" is used to describe events, event handlers and methods, when each is a different thing.

Actually, no, the word event is used by me to describe... events, as a process. Not an event data type, not methods that act as event handlers, and not methods (though wouldn't that be the event handler, the method that handles said event).




Back at OP...

events are just like delegates. And delegates are references to methods. And a method when ran from a given thread, will be running on that given thread, unless explicitly told to run on another.
 
yes i was playing around with the background worker and tried writing to a textbox. i received an error informing me that ' Cross-thread operation not valid: Control 'TextBox1' accessed from a thread other than the thread it was created on'. so asumed that i could not write directly to the UI thread in which the textbox control was situated because it was another thread . i was thinking that perhaps i would need to load the values into a global variable and run code on the UI to take the global values and place into a textbox?? how would i be able to write to a textbox on the UI in this case? do you have an example i could study?
 
BUT there is the protected OnClick event defined for all Controls that can be called by custom code
OnClick is not an event. OnClick is a method; specifically, it is the method that raises the Click event.
 
how would i be able to write to a textbox on the UI in this case? do you have an example i could study?
I think you missed this explanation of how you use BackgroundWorker to report to UI:
If you need to update the UI you cannot do it in the DoWork event handler or any method called from the DoWork event handler, because they are all executed on the same background thread. To update the UI during the background operation you call the ReportProgress method and handle the ProgressChanged event. Because the ProgressChanged event is raised on the UI thread, your event handler is executed on the UI thread, so you can update the UI. If you need to update the UI when the background operation is complete, you handle the RunWorkerCompleted event, which is also raised on the UI thread.
In addition, not sure if it was mentioned, to pass final result with BgW you set e.Result (any object, also composite) in DoWork handler, and retrieve it from the RunWorkerCompleted event.
 
JohnH thanks for pointing that part of the message out. the trouble is i am struggling to understand the content of it. i haven't been using vb.net for very long so i am afraid i am not up with the terminology... i am trying to find as much information on the web as i can about it but it seems to be a bit thin on the ground. i felt an example would help me see the process more clearly.

thanks in advance.
 
Back
Top