问题
In C# is there any difference between using a delegate to do some work asynchronously (calling BeginInvoke()) and using a ThreadPool thread as shown below
public void asynchronousWork(object num)
{
//asynchronous work to be done
Console.WriteLine(num);
}
public void test()
{
Action<object> myCustomDelegate = this.asynchronousWork;
int x = 7;
//Using Delegate
myCustomDelegate.BeginInvoke(7, null, null);
//Using Threadpool
ThreadPool.QueueUserWorkItem(new WaitCallback(asynchronousWork), 7);
Thread.Sleep(2000);
}
Edit:
BeginInvoke makes sure that a thread from the thread pool is used to execute the asynchronous code , so is there any difference?
回答1:
Joe Duffy, in his Concurrent Programming on Windows book (page 418), says this about Delegate.BeginInvoke:
All delegate types, by convention offer a BeginInvoke and
EndInvokemethod alongside the ordinary synchronousInvokemethod. While this is a nice programming model feature, you should stay away from them wherever possible. The implementation uses remoting infrastructure which imposes a sizable overhead to asynchronous invocation. Queue work to the thread pool directly is often a better approach, though that means you have to co-ordinate the rendezvous logic yourself.
EDIT: I created the following simple test of the relative overheads:
int counter = 0;
int iterations = 1000000;
Action d = () => { Interlocked.Increment(ref counter); };
var stopwatch = new System.Diagnostics.Stopwatch();
stopwatch.Start();
for (int i = 0; i < iterations; i++)
{
var asyncResult = d.BeginInvoke(null, null);
}
do { } while(counter < iterations);
stopwatch.Stop();
Console.WriteLine("Took {0}ms", stopwatch.ElapsedMilliseconds);
Console.ReadLine();
On my machine the above test runs in around 20 seconds. Replacing the BeginInvoke call with
System.Threading.ThreadPool.QueueUserWorkItem(state =>
{
Interlocked.Increment(ref counter);
});
changes the running time to 864ms.
来源:https://stackoverflow.com/questions/10340871/difference-between-delegate-begininvoke-and-using-threadpool-threads-in-c-sharp