Level Extreme platform
Subscription
Corporate profile
Products & Services
Support
Legal
Français
Waiting for background thread pattern
Message
From
18/05/2011 15:36:45
Timothy Bryan
Sharpline Consultants
Conroe, Texas, United States
 
 
General information
Forum:
ASP.NET
Category:
Coding, syntax and commands
Environment versions
Environment:
C# 4.0
OS:
Windows XP SP2
Application:
Desktop
Miscellaneous
Thread ID:
01510997
Message ID:
01511021
Views:
44
>>Have you looked at the new Asynch stuff? http://msdn.microsoft.com/en-us/vstudio/async.aspx
>>
>>>Hi all,
>>>
>>>I am making some changes to an application to help with performance. On the startup currently there are lots of objects and initialization that needs to be performed and currently this is blocking the UI thread. I am moving these things to a Background worker thread so the UI can continue to load and present. The question is I am looking for an appropriate pattern or design that I could implement to know if the user attempts something that requires the Background worker to be done before the worker is completed it would wait. This means either the worker is done and the user action could continue; or the user attempt is waited pending the completion of the worker thread. In addition, if the user exits, I would need to cancel the worker thread if it is still running.
>>>
>>>I have experimented with a couple of mechanisms but thinking there may already be some design pattern for this.
>>>Thanks
>
>Hi,
>Don't know if there's a generally accepted pattern. In this situation I usually end up with something like:
using System;
>using System.ComponentModel;
>
>namespace ConsoleApplication6
>{
>    class Program
>    {
>        static bool ThreadCancelled = false;
>        static SomethingTheWorkerBuilds theResult;
>        static void Main(string[] args)
>        {
>            BackgroundWorker bg = new BackgroundWorker();
>            bg.WorkerSupportsCancellation = true;
>            bg.WorkerReportsProgress = true;
>            bg.DoWork += new DoWorkEventHandler(bg_Work);
>            bg.ProgressChanged += new ProgressChangedEventHandler(bg_ProgressChanged);
>            bg.RunWorkerCompleted += new RunWorkerCompletedEventHandler(bg_RunWorkerCompleted);
>            bg.RunWorkerAsync();
>            System.Threading.Thread.Sleep(5000);
>
>            //Cancel the thread:
>            //bg.CancelAsync();
> 
>            DoSomethingThatRequiresThreadCompleted();
>            Console.ReadLine();
>        }
>
>        static void bg_ProgressChanged(object sender, ProgressChangedEventArgs e)
>        {
>            Console.WriteLine("Progress {0}", e.ProgressPercentage);
>        }
>
>        static void bg_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
>        {
>            if (e.Cancelled)
>                ThreadCancelled = true;
>            else
>                theResult = (SomethingTheWorkerBuilds)e.Result;
>        }
>
>        static void bg_Work(object sender, DoWorkEventArgs e)
>        {
>
>                BackgroundWorker bg = sender as BackgroundWorker;
>                for (int i = 0; i < 10; i++)
>                {
>                    if (bg.CancellationPending)
>                    {
>                        e.Cancel = true; break;
>                    }
>                    System.Threading.Thread.Sleep(1000);
>                    bg.ReportProgress(i);
>                }
>                e.Result = new SomethingTheWorkerBuilds();
>        }
>
>        static void DoSomethingThatRequiresThreadCompleted()
>        {
>            Console.WriteLine("Waiting for thread");
>            while (theResult==null  && !ThreadCancelled) { }
>            if (ThreadCancelled)
>                Console.WriteLine("Thread cancelled");
>            else
>                //Carry on
>                Console.WriteLine(theResult.Text);
>        }
>    }
>
>    class SomethingTheWorkerBuilds
>    {
>        public string Text = "Hello World";
>    }
>}
(ISTR I couldn't trust using BackgroundWorker.IsBusy because that would return false before 'theResult' was populated - but I might be wrong)

Hi Viv,

This is pretty close to what I am doing except checking for "theResult". Mine doesn't build an object, but it could still populate some value.
More specifically what I am doing is speeding up an application that has way too much to do before it displays a login screen. So I thought a little smoke and mirror and a little background work would be better. I am displaying the login form right away but just before I kick off a background worker to get all that stuff done. If the user clicks the login button before the background work finishes, then I will just show a WPF animation of activity so it can finish up plus perform the login process over a web service. Since some of the process can be done even after the login is completed but before the main window is displayed, I am breaking this up into a couple of background workers and run one, then the second. As long as the first is done I can let them login while the other keeps working. Hopefully I get all the synchronization in order and it will be good.

sorry for the long winded answer to say, I appreciate your input. It did help me in some forms.
Craig, I am looking at the link you posted.
Thanks to both
Tim
Timothy Bryan
Previous
Next
Reply
Map
View

Click here to load this message in the networking platform