Why to choose System.Threading over BackgroundWorker? - c#

Why would I decide to choose working directly with System.Threading over BackgroundWorker if the last one abstracts for me the treading managemnet?
I can't see cases where I couldn't use BackgroundWorker to replace System.Threading

BackgroundWorker has been around since .NET 2.0 and was intended to aid in writing code that will run in a background thread and not bog down the UI thread. It originally appeared with Windows Forms, but also works with WPF or any future UI framework that registers a synchronization context. It allows you to report progress and results back to the UI thread without having to deal with InvokeRequired/BeginInvoke as well supports cancellation.
The Task Parallel Library (TPL) was introduced in .NET 4 and is intended to model asynchronous tasks. These tasks are asynchronous and may or may not be run on another thread. Examples of something that doesn't run on another thread is asynchronous IO and tasks that need to run on the UI (while still being asynchronous). This task metaphor also supports futures (or continuations) so that you can chain tasks together with ContinueWith, sometimes using specific synchronization contexts so that you can do things like run a task on a UI thread (to update the UI, for example).
Tasks also support cancellation and multiple tasks can share a cancellation token so a requested cancellation cancels multiple tasks.
One of the differences is a Task doesn't have an inherent method of reporting progress back to the UI. Of course it's possible, but it's not built into the interfaces. Tasks also support cancellation.
If you only have one thing you want to do in the background and you specifically want to communicate back to a UI like report progress, I would recommend BackgroundWorker. Otherwise I generally recommend using Task<T> (or Task if no result is necessary). Task is inherently used in the C# 5 async/await syntax...

I hope you attempt to think about the intention of each approaches.
BackgroundWorker was designed for Windows Forms mainly at the very beginning (though it can be used in WPF as well), and it only offers some functionality of asynchronous operation. Compared it to all classes under System.Threading, you can see BackgroundWorker obviously is built upon them.
With all classes under System.Threading, you can build your own BackgroundWorker and enjoy more functionality and control over your code. The difficulty here is sharp learning curve, and debugging challenges.
So if you think BackgroundWorker is enough, keep using it. If you find something missing, building blocks in System.Threading can be your helpers.
In .NET Framework 4, Microsoft designs another set of classes upon System.Threading, named Task-based Asynchronous Pattern,
http://www.microsoft.com/en-us/download/details.aspx?id=19957
Using it, you can almost forget about BackgroundWorker, as it offers much more functionality and give you enough control, while does not require you to dive into the complexity of working with System.Threading directly.

I have a blog post on the subject.
In short, you should use async Tasks if you possibly can. Thread does provide some additional "knobs" - such as Priority - but usually those knobs are not necessary, and programmers often turn them the wrong way anyway.

For one you cannot set scheduling priority on BackgroundWorker but you can on a Thread.
Thread.Priority Property
Comments that question my answer continue to refer to Task and ThreadPool. The stated question is not about Task nor ThreadPool and neither is my answer.
Please refer to the code sample from the link above. It clearly demonstrates assigning priority prior to starting the thread and control over starting the thread.
Complete code sample:
PriorityTest priorityTest = new PriorityTest();
ThreadStart startDelegate = new ThreadStart(priorityTest.ThreadMethod);
Thread threadOne = new Thread(startDelegate);
threadOne.Name = "ThreadOne";
Thread threadTwo = new Thread(startDelegate);
threadTwo.Name = "ThreadTwo";
threadTwo.Priority = ThreadPriority.BelowNormal;
threadOne.Start();
threadTwo.Start();
// Allow counting for 10 seconds.
Thread.Sleep(10000);
priorityTest.LoopSwitch = false;
I tested this and ThreadTwo starts and finishes on ThreadPriority.BelowNormal. In my test threadOne processes about 10X as threadTwo.
BackGroundWorker has no Priority property. A BackgroundWorker starts with the default priority of Normal. BackgroundWorker thread priority can be changed in DoWork but changing the priority of a thread once the work has started is clearly not the same.

Related

WPF Dispatcher on non-UI thread

According to MSDN, Dispatcher provides services for managing the queue of work items for a thread.
A simple question. I want to use Dispatcher just for that: as a queue of work items (posted via Dispatcher.BeginInvoke) which my background thread will serve in a serial manner.
I don't want to make this thread an STA thread and I don't need to pump Windows messages on it. There will be no UI on this thread.
Is it a legitimate way of using Dispatcher?
Is it a legitimate way of using Dispatcher?
You could use a secondary thread with a Dispatcher, but it's rather uncommon. This is usually done so that different parts of the UI run on different UI threads. A dispatcher thread will process Windows messages, and must be STA. Also, technically speaking the processing isn't strictly FIFO since dispatched items are queued with a priority.
That said, even though it wasn't designed to be used without a UI, you could use it that way.
Alternatives:
1) AsyncContextThread is a simple thread with a work queue from my AsyncEx NuGet library:
private readonly AsyncContextThread _thread = new AsyncContextThread();
...
_thread.Factory.StartNew(() => { ... });
The AsyncContextThread type provides a SynchronizationContext for the code it runs, so async continuations will resume on the same thread by default.
2) If it only matters that the requests are processed serially, and doesn't actually matter which thread they run on, then you can use a task scheduler to instruct the thread pool to run your requests one at a time, as such:
private readonly TaskFactory _factory = new TaskFactory(
new ConcurrentExclusiveSchedulerPair().ExclusiveScheduler);
_factory.StartNew(() => { ... });
Short answer:
If you need to actually do work with Dispatcher runtime components, such as System.Windows.Media.Imaging, then I have an answer for you. If you're not using Dispatcher runtime components then don't even consider using the Dispatcher runtime. Use the Task Parallel Library (TPL) instead.
Long answer:
I've built and use this DispatcherTaskScheduler implementation in high volume production services. You can configure it with as many threads as you'd like it to have a pool of (default is number of cores) and it will take care of spinning up those threads, initializing them with the Dispatcher runtime and then queuing and dispatching work to them. Works with great with TPL, TPL DataFlow, SynchronizationContext style programming (e.g. async/await), etc.
Basic usage looks something like this:
Task.Factory.StartNew(() =>
{
// Do anything you want with Dispatcher components here
},
CancellationToken.None,
TaskCreationOptions.None,
DispatcherTaskFactory.Default);
If you configure your own instance (e.g. you want more threads) then just replace DispatcherTaskFactory.Default with your instance instead. My advice is to not configure more threads than cores (just use the Default instance) and make sure you try to only do Dispatcher runtime work on these threads.
As I mentioned, I use this implementation in several parts of our software system related to image processing that are core to our business and endure high volume loads and it's proven absolutely bullet proof for us.
Finally, the disclaimer: Microsoft doesn't really support the Dispatcher runtime being used like this.

Which threads work method I need to use?

I have audio player application (c# .NET 4.0 WPF) that gets an audio-stream from the web and plays it. The app also displays waveforms and spectrums and saves the audio to local disk. It also does a few more things.
My quetion is when I recive a new byte packet from the web and I need to play them (and maybe write them to local disk etc.), do I need use threads? I try to do all the things with the main thread and it seems to work well.
I can work with threadpool for every bytes packet that I received in my connection. Would this be a reasonable approach?
For this you can use the Task Parallel Library (TPL). The Task Parallel Library (TPL) is a set of public types and APIs in the System.Threading and System.Threading.Tasks namespaces in the .NET Framework version 4. The purpose of the TPL is to make developers more productive by simplifying the process of adding parallelism and concurrency to applications. The TPL scales the degree of concurrency dynamically to most efficiently use all the processors that are available. In addition, the TPL handles the partitioning of the work, the scheduling of threads on the ThreadPool, cancellation support, state management, and other low-level details.
Another option (if the operations you were performing were sufficiently long running) is the BackgroundWorker class. The BackgroundWorker component gives you the ability to execute time-consuming operations asynchronously ("in the background"), on a thread different from your application's main UI thread. To use a BackgroundWorker, you simply tell it what time-consuming worker method to execute in the background, and then you call the RunWorkerAsync method. Your calling thread continues to run normally while the worker method runs asynchronously. When the method is finished, the BackgroundWorker alerts the calling thread by firing the RunWorkerCompleted event, which optionally contains the results of the operation. This may not be the best option for you if you have many operations to undertake sequentially.
The next alternative that has been largely replaced by the TPL, is the Thread Class. This is not so easy to use at the TPL and you can do everything using the TPL as you can using the Thread Class (well almost) and the TPL is much more user friendly.
I hope this helps.
I suggest using 2 threads: in one you are downloading packets from web and putting them in queue(it can be UI thread if you are using async download operation) and in another thread you are analyzing queue and processing packets from it.

Background Threads in Windows Phone

So far during my experience in Windows Phone 7 application development I notices there are different ways to runs an action in an asynchronous thread.
System.Threading.Thread
System.ComponentModel.BackgroundWorker
System.Threading.ThreadPool.QueueUserWorkItem()
I couldn't see any tangible difference between these methods (other than that the first two are more traceable).
Is there any thing you guys consider before using any of these methods? Which one would you prefer and why?
The question is kinda answered but the answers are a little short on detail (IMO).
Lets take each in turn.
System.Threading.Thread
All the threads (in the CLR anyway) are ultimately represented by this class. However you probably included this to query when we might want to create an instance ourselves.
The answer is rarely. Ordinarily the day-to-day workhorse for dispatching background tasks is the Threadpool. However there are some circumstances where we would want to create our own thread. Typically such a thread would live for most of the app runtime. It would spend most of its life in blocked on some wait handle. Occasionally we signal this handle and it comes alive to do something important but then it goes back to sleep. We don't use a Threadpool work item for this because we do not countenance the idea that it may queue up behind a large set of outstanding tasks some of which may themselves (perhaps inadverently) be blocked on some other wait.
System.ComponentModel.BackgroundWorker
This is friendly class wrapper around the a ThreadPool work item. This class only to the UI oriented developer who occasionally needs to use a background thread. Its events being dispatched on the UI thread makes it easy to consume.
System.Threading.ThreadPool.QueueUserWorkItem
This the day-to-day workhorse when you have some work you want doing on a background thread. This eliminates the expense of allocating and deallocating individual threads to perform some task. It limits the number of thread instances to prevent too much of the available resources being gobbled up by too many operations try to run in parallel.
The QueueUserWorkItem is my prefered option for invoking background operations.
It arguably depends on what you are trying to do, you have listed 3 very different threading models.
Basic threading
Designed for applications with a seperate UI thread.
Managed thread pool
Have you read MSDN etc...
http://www.albahari.com/threadin
Http://msdn.microsoft.com/en-us/library/aa645740(v=vs.71).aspx
You don't state "what for", but
Basic Thread - quite expensive, not for small jobs
Backgroundworker - mostly for UI + Progressbar work
ThreadPool - for small independent jobs
I think the TPL is not supported in SL, which is a pity.
The background worker tends to be better to use when your UI needs to be update as your thread progresses because it handles invoking the call back functions (such as the OnProgress callback) on the UI thread rather than the background thread. The other two don't do this work. It is up to you to do it.

Task parallel library replacement for BackgroundWorker?

Does the task parallel library have anything that would be considered a replacement or improvement over the BackgroundWorker class?
I have a WinForms application with a wizard-style UI, and it does some long-running tasks. I want to be able to have a responsive UI with the standard progress bar and ability to cancel the operation. I've done this before with BackgroundWorker, but I'm wondering if there are some TPL patterns that can be used instead?
The Task class is an improvement over the BackgroundWorker; it naturally supports nesting (parent/child tasks), uses the new cancellation API, task continuations, etc.
I have an example on my blog, showing the old BackgroundWorker way of doing things and the new Task way of doing things. I do have a small helper class for tasks that need to report progress, because I find the syntax rather awkward. The example covers result values, error conditions, cancellation, and progress reporting.
Background worker is still a valid way of achieving this - if you are running multiple large operations concurrently then the parallel extensions would be worth considering, if its just the one then I would stick with the backgroundworker.

.NET threading solution for long queries

Senerio
We have a C# .Net Web Application that records incidents. An external database needs to be queried when an incident is approved by a supervisor. The queries to this external database are sometimes taking a while to run. This lag is experienced through the browser.
Possible Solution
I want to use threading to eliminate the simulated hang to the browser. I have used the Thread class before and heard about ThreadPool. But, I just found BackgroundWorker in this post.
MSDN states:
The BackgroundWorker class allows you to run an operation on a separate, dedicated thread. Time-consuming operations like downloads and database transactions can cause your user interface (UI) to seem as though it has stopped responding while they are running. When you want a responsive UI and you are faced with long delays associated with such operations, the BackgroundWorker class provides a convenient solution.
Is BackgroundWorker the way to go when handling long running queries?
What happens when 2 or more BackgroundWorker processes are ran simultaneously? Is it handled like a pool?
Yes, BackgroundWorker can significantly simplify your threading code for long-running operations. The key is registering for the DoWork, ProgressChanged, and RunWorkerCompleted events. These help you avoid having to have a bunch of synchronization objects passed back and forth with the thread to try to determine the progress of the operation.
Also, I believe the progress events are called on the UI thread, avoiding the need for calls to Control.Invoke to update your UI.
To answer your last question, yes, threads are allocated from the .NET thread pool, so you while you may instantiate as many BackgroundWorker objects as you'd like, you can only run as many concurrent operations as the thread pool will allow.
If you're using .NET 4 (or can use the TPL backport from the Rx Framework), then one nice option is to use a Task created with the LongRunning hint.
This provides many options difficult to accomplish via the ThreadPool or BackgroundWorker, including allowing for continuations to be specified at creation time, as well as allowing for clean cancellation and exception/error handling.
I had ran in similar situation with long running queries. I used the asynchronous invoke provided by delegates. You can use the BeginInvoke method of the delegate.
BackgroundWrokerks are just like any other threads, accept they can be killed or quit, w/out exiting the main thread and your application.
ThreadPool uses a pool of BackgroundWorkers. It is the preferred way of most multi threading scenarios because .net manages threads for you, and it re-uses them instead of creating new ones as needed which is a expensive process.
Such threading scenarios are great for processor intensive code.
For something like a query which happens externally, you also have the option of asynchronous data access. You can hand off the query request, and give it the name of your callback method, which will be called when query is finished and than do something with the result (i.e. update UI status or display returned data)..
.Net has inbuilt support for asynchronous data querying
http://www.devx.com/dotnet/Article/26747

Categories