Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book...
-
Upload
lester-hampton -
Category
Documents
-
view
218 -
download
0
Transcript of Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book...
![Page 1: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/1.jpg)
Chapter 13
Working with Threads
![Page 2: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/2.jpg)
Copyright 2006 Thomas P. Skinner 2
Other Reference
• The book Programming Microsoft .NET by Jeff Prosise.
• Chapter 14 is excellent.
• This book is available through our MSDNAA program in the MELL collection.
• I used much of this material.
![Page 3: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/3.jpg)
Copyright 2006 Thomas P. Skinner 3
Basics
• The threads of a process all use the same address space and share all resources.
• Each thread has its own stack.• Each thread can has specific properties such as
a unique name, priority, etc.• Threads can share objects, but must be sure to
avoid the problem of race conditions (mutual exclusion) by using the synchronization and mutual exclusion features of the .NET FCL.
![Page 4: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/4.jpg)
Copyright 2006 Thomas P. Skinner 4
Basics - Contd.
• Not all of the .NET FCL is “thread safe.”
• This means that two or more processes can not invoke properties or methods of the same instance of such an object at the same time.
• Locking must be employed.
• The FCL documentation specifically addresses the thread safety of the class.
![Page 5: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/5.jpg)
Copyright 2006 Thomas P. Skinner
5
An Example of why Threads are Needed
No Response - Form1.cs
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
namespace NoResponse
{
public partial class Form1 : Form
{
![Page 6: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/6.jpg)
Copyright 2006 Thomas P. Skinner
6
Example – Contd. public Form1() { InitializeComponent(); } private void Form1_MouseClick(object sender, MouseEventArgs e) { Cursor = Cursors.WaitCursor; //Loop for approximately 30 seconds (depends on //system speed) long i = 3000000000; while (--i>0) ; Cursor = Cursors.Default; } }}
![Page 7: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/7.jpg)
Copyright 2006 Thomas P. Skinner 7
Ooops! The GUI Doesn’t Respond
![Page 8: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/8.jpg)
Copyright 2006 Thomas P. Skinner 8
The Thread Class
• In System.Threading namespace.• Useful properties:
1. CurrentThread – returns a reference to the callers thread
2. Name – a string representing the programmer assigned name
3. Priority – the thread priority (may be set to a non-default value)
4. IsAlive – true if thread is running (not terminated)
![Page 9: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/9.jpg)
Copyright 2006 Thomas P. Skinner 9
Starting a Thread
Void myMethod()
{
//do something
}
//-------------------------
ThreadStart startMethod = new ThreadStart(myMethod);
Thread myThread = new Thread(startMethod);
myThread.Start();
![Page 10: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/10.jpg)
Copyright 2006 Thomas P. Skinner 10
ThreadStart
• The method to be started by the thread can be an instance method or a static method.
• You don’t need to worry about how the thread is able to determine the object instance (this).
• Use static fields, properties, and methods to handle data shared between threads (with locks as needed).
• .Remember, there are no global variables in C#!
![Page 11: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/11.jpg)
Copyright 2006 Thomas P. Skinner
11
Keep the GUI Alive
Good Response - First Tryusing System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Threading;
namespace GoodResponse
{
public partial class Form1 : Form
![Page 12: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/12.jpg)
Copyright 2006 Thomas P. Skinner
12
Keep the GUI Alive
{
private Thread workerThread;
private ThreadStart workerStart;
public Form1()
{
InitializeComponent();
}
private void Form1_MouseClick(object sender, MouseEventArgs e)
{
//Don't creater more than one worker thread
if (workerThread == null)
![Page 13: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/13.jpg)
Copyright 2006 Thomas P. Skinner
13
Keep the GUI Alive { workerStart = new ThreadStart(WorkerThread); workerThread = new Thread(workerStart); workerThread.Start(); } } private void WorkerThread() { Cursor = Cursors.WaitCursor; //Loop for approximately 30 seconds (depends on //system speed) long i = 3000000000; while (--i > 0) ; Cursor = Cursors.Default; workerThread = null; } }}
![Page 14: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/14.jpg)
Copyright 2006 Thomas P. Skinner 14
Cross Thread Problem
• If you run this program in the debugger VS 2005 is smart enough to provide the following warning shown below.
• We will fix this later.
![Page 15: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/15.jpg)
Copyright 2006 Thomas P. Skinner 15
Terminating a Thread
• A thread terminates when it returns from the method used for its start.
• A thread can be suspended by the Suspend method.
• The Resume method starts the thread running again.
• The Thread.Sleep method suspends a thread for a specific number of milliseconds. This is a static method.
![Page 16: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/16.jpg)
Copyright 2006 Thomas P. Skinner 16
Foreground vs. Background Threads
• By default a thread is a foreground thread.• An appliication doesn’t terminate until all foreground threads
terminate.• This is VERY insidious.• Consider the following example.• The thread is started and the main application is closed.• It looks like the application is gone, but task manager shows it
is still running and burning up CPU time.• It doesn’t appear in the task bar and is completely invisible to
the user.• BEWARE!!!! I made this mistake with an early version of the
dining Philosopher problem. My system got slower and slower until I realized that there were many philosopher processes running.
![Page 17: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/17.jpg)
Copyright 2006 Thomas P. Skinner
17
Bad Thread
private void button1_Click(object sender, System.EventArgs e){if(t==null){t = new Thread(new ThreadStart(ThreadProc));t.Start();
}elseMessageBox.Show("Thread running!");
}private Thread t;private void ThreadProc(){while(true);
}
![Page 18: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/18.jpg)
Copyright 2006 Thomas P. Skinner 18
Thread still
running
![Page 19: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/19.jpg)
Copyright 2006 Thomas P. Skinner 19
Solution• Make the thread a background thread.
• Background threads are terminated when the foreground threads complete.
private void button1_Click(object sender, System.EventArgs e){if(t==null){t = new Thread(new ThreadStart(ThreadProc));t.IsBackground=true;t.Start();
}elseMessageBox.Show("Thread running!");
}
![Page 20: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/20.jpg)
Copyright 2006 Thomas P. Skinner
20
Fixed up Example
Good Response - Form1.cs using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Threading;
namespace GoodResponse
{
public partial class Form1 : Form
{
![Page 21: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/21.jpg)
Copyright 2006 Thomas P. Skinner
21
Fixed up Example
private Thread workerThread;
private ThreadStart workerStart;
public Form1()
{
InitializeComponent();
}
private void Form1_MouseClick(object sender, MouseEventArgs e)
{
//Don't creater more than one worker thread
if (workerThread == null)
{
![Page 22: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/22.jpg)
Copyright 2006 Thomas P. Skinner
22
Fixed up Example workerStart = new ThreadStart(WorkerThread); workerThread = new Thread(workerStart); workerThread.IsBackground = true; workerThread.Start(); } } private void WorkerThread() { MessageBox.Show("Worker thread started."); //Loop for approximately 30 seconds (depends on //system speed) long i = 3000000000; while (--i > 0) ; MessageBox.Show("Worker thread terminated."); workerThread = null; } }}
![Page 23: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/23.jpg)
Copyright 2006 Thomas P. Skinner 23
Communicating with a Thread
• Shared memory is the easiest.
• Unfortunately we need to worry about race conditions.
• C# provides some easy to use mechanisms to solve the mutual exclusion problem.
![Page 24: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/24.jpg)
Copyright 2006 Thomas P. Skinner 24
Cancelling a Thread Gracefully
• Rather than aborting the thread, which has its problems, we can use a flag to alert the worker thread that it should abort.
• This requires inserting a check inside whatever loop is used by the worker thread.
• We must assure that this flag is checked frequently for good application response.
• A simple example follows.
![Page 25: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/25.jpg)
Copyright 2006 Thomas P. Skinner
25
Cancel Example
Cancel Thread - Form1.cs
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Threading;
namespace CancelThread
{
public partial class Form1 : Form
{
![Page 26: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/26.jpg)
Copyright 2006 Thomas P. Skinner
26
Cancel Example
private Thread workerThread;
private ThreadStart workerStart;
private bool cancel = false;
public Form1()
{
InitializeComponent();
}
private void Form1_Click(object sender, EventArgs e)
{
//Don't create more than one worker thread
if (workerThread == null)
{
![Page 27: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/27.jpg)
Copyright 2006 Thomas P. Skinner
27
Cancel Example
workerStart = new ThreadStart(WorkerThread);
workerThread = new Thread(workerStart);
workerThread.IsBackground = true;
cancel = false;
workerThread.Start();
}
}
private void WorkerThread()
{
MessageBox.Show("Worker thread started.");
//Loop for approximately 30 seconds //(depends on system speed)
long i = 3000000000;
![Page 28: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/28.jpg)
Copyright 2006 Thomas P. Skinner
28
Cancel Example
while (--i > 0) if(cancel) break;
MessageBox.Show("Worker thread terminated.");
workerThread = null;
}
private void cancelButton_Click(object sender, EventArgs e)
{
cancel = true;
}
}
}
![Page 29: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/29.jpg)
Copyright 2006 Thomas P. Skinner 29
The Form
![Page 30: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/30.jpg)
Copyright 2006 Thomas P. Skinner 30
Using Events with Threads
• It will probably cross your mind that the use of C# events might be a simple way to invoke a method in one thread from another.
• Unfortunately this is illusory. Events work perfectly, but the handler for the event is executed on the thread that triggered the event.
• There is a subtle way for us to accomplish asynchronous method invocation across thread boundaries.
![Page 31: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/31.jpg)
Copyright 2006 Thomas P. Skinner 31
Control.Invoke()
• Any class derived from control has a method named Invoke.
• If it is called with a reference to a delegate, the delegate is invoked on the thread that owns the controls underlying window.
• This is perfect for invoking a method in a UI thread from a worker thread.
![Page 32: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/32.jpg)
Copyright 2006 Thomas P. Skinner
32
Invoke Example
Invoke Example - Form1.cs
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Threading;
namespace InvokeExample
{
public partial class Form1 : Form
{
![Page 33: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/33.jpg)
Copyright 2006 Thomas P. Skinner
33
Invoke Example
private Thread workerThread;
private ThreadStart workerStart;
private bool cancel = false;
private delegate void Done();
private Done done;
public Form1()
{
InitializeComponent();
done = new Done(ThreadDone);
}
private void Form1_Click(object sender, EventArgs e)
![Page 34: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/34.jpg)
Copyright 2006 Thomas P. Skinner
34
Invoke Example
{
//Don't create more than one worker thread
if (workerThread == null)
{
workerStart = new ThreadStart(WorkerThread);
workerThread = new Thread(workerStart);
workerThread.IsBackground = true;
cancel = false;
Cursor = Cursors.WaitCursor;
workerThread.Start();
}
}
![Page 35: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/35.jpg)
Copyright 2006 Thomas P. Skinner
35
Invoke Example
private void WorkerThread()
{
//Loop for approximately 30 seconds (depends //on system speed)
long i = 3000000000;
while (--i > 0) if(cancel) break;
Invoke(done);
//done();
workerThread = null;
}
![Page 36: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/36.jpg)
Copyright 2006 Thomas P. Skinner
36
Invoke Example
private void cancelButton_Click(object sender, EventArgs e)
{
cancel = true;
}
private void ThreadDone()
{
Cursor = Cursors.Arrow;
}
}
}
![Page 37: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/37.jpg)
Copyright 2006 Thomas P. Skinner 37
Thread Safety
• If we execute a method in more than one thread at a time and there is any shared data we need to ensure that the method is thread safe.
• Race conditions are the root cause of this problem.• You shjould be familiar with race conditions from
operating systems theory.• The .NET documentation usually mentions if a method is
thread safe.• It is usually a good idea to err on the side of caution.• Don't execute methods in two or more threads that
operate on behalf of the same object instance.
![Page 38: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/38.jpg)
Copyright 2006 Thomas P. Skinner 38
Mutual Exclusion
• The Monitor class is used to guarantee mutual exclusion. (Not the same as the classic monitor from operating systems.)
• We learned in operating systems how important mutual exclusion is when in a critical section.
• Monitor.Enter(Object obj) and Monitor.Exit(Object obj) bracket a critical section.
• Careful – don’t use a value type as argument to Enter and Exit. A value type will be boxed and therefore become a new object. Mutual exclusion will not be guaranteed since each thread that boxes the value type gets a new reference type instead.
![Page 39: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/39.jpg)
Copyright 2006 Thomas P. Skinner 39
Mutual Exclusion – Contd.
• Any object can be used to obtain the lock, but usually we use the object containing the critical data.
• Normally we use the Monitor with a try finally block to guarantee that Exit will be called.Monitor.Enter(obj);
try
{ … }
finally {Monitor.Exit(obj);}
![Page 40: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/40.jpg)
Copyright 2006 Thomas P. Skinner 40
C# lock Keyword
• C# includes the lock keyword that is functionally equivalent to the previous try finally construct using the Monitor.
• It is simpler.lock(obj)
{
//critical section code
}
• That’s it!
![Page 41: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/41.jpg)
Copyright 2006 Thomas P. Skinner 41
Timer
• The Thread.Sleep method can be used to suspend a thread for some number of milliseconds.
• The resolution of this timer is somewhat worse than a millisecond and shouldn’t be used for exact timing purposes.
• We often insert brief delays in applications when we know, for example, that an external event needs to be allowed time to respond.
• We gain better efficiency by not burning up CPU cycles.• Of course if we can make a blocking call that is always a
better choice rather than some type of polling.
![Page 42: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/42.jpg)
Copyright 2006 Thomas P. Skinner
42
Progress Bar Example
SleepEx - Form1.cs
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Threading;
namespace SleepEx
{
public partial class Form1 : Form
{
![Page 43: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/43.jpg)
Copyright 2006 Thomas P. Skinner
43
Progress Bar Example
private Thread workerThread;
private ThreadStart workerStart;
private delegate void Step();
private Step step;
public Form1()
{
InitializeComponent();
step = new Step(StepBar);
}
private void startButton_Click(object sender, EventArgs e)
{
//Don't create more than one worker thread
![Page 44: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/44.jpg)
Copyright 2006 Thomas P. Skinner
44
Progress Bar Example
if (workerThread == null)
{
pBar.Value = 0; //reset progress bar
workerStart = new ThreadStart(WorkerThread);
workerThread = new Thread(workerStart);
workerThread.IsBackground = true;
workerThread.Start();
}
}
private void WorkerThread()
{
![Page 45: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/45.jpg)
Copyright 2006 Thomas P. Skinner
45
Progress Bar Example
for (int i = 0; i < 30; ++i)
{
Thread.Sleep(1000);
Invoke(step);
}
workerThread = null;
}
private void StepBar()
{
pBar.PerformStep();
}
}
}
![Page 46: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/46.jpg)
Copyright 2006 Thomas P. Skinner 46
Output
![Page 47: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/47.jpg)
Copyright 2006 Thomas P. Skinner 47
Thread Synchronization
• How can one thread wait for another thread without constantly examining a memory location to see if it has changed?
• Semaphores are a classic solution.
• .NET includes an easy alternative that I will demonstrate.
![Page 48: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/48.jpg)
Copyright 2006 Thomas P. Skinner 48
AutoResetEvent
• AutoResetEvent objects solve synchronization problems.
• If we want one thread to wait for an operation to be completed in another thread we use the AutoResetEvent class.
• The WaitOne and Set methods are similar to Wait and Signal as used in operating system texts.
![Page 49: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/49.jpg)
Copyright 2006 Thomas P. Skinner 49
Join
• We can wait for a thread to terminate by using the Join method.
Thread myThread;
//create and start the thread
myThread.Join(); //waits for thread to terminate
![Page 50: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/50.jpg)
Copyright 2006 Thomas P. Skinner
50
FlipFLop Example without Synchronization
FlipFlop without synchronization
using System;
using System.Collections.Generic;
using System.Text;
using System.Threading;
using System.IO;
namespace FlipFlop
{
class FlipFlop
{
static void Main(string[] args)
{
Thread flip = new Thread(new ThreadStart(flipT));
![Page 51: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/51.jpg)
Copyright 2006 Thomas P. Skinner
51
FlipFLop Example without Synchronization
Thread flop = new Thread(new ThreadStart(flopT));
flip.Start();
flop.Start();
flip.Join();
flop.Join();
Console.WriteLine("Finished");
}
static void flipT()
{
for(int i=0;i<5;++i)
{
Console.WriteLine("Flip");
![Page 52: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/52.jpg)
Copyright 2006 Thomas P. Skinner
52
FlipFLop Example without Synchronization
}
}
static void flopT()
{
for (int i = 0; i < 5; ++i)
{
Console.WriteLine("Flop");
}
}
}
}
![Page 53: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/53.jpg)
Copyright 2006 Thomas P. Skinner 53
Output
![Page 54: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/54.jpg)
Copyright 2006 Thomas P. Skinner
54
FliFlop Example with Synchronization
FlipFlop - FlipFlop.cs
using System;
using System.Collections.Generic;
using System.Text;
using System.Threading;
using System.IO;
namespace FlipFlop
{
class FlipFlop
{
static AutoResetEvent flipE = new AutoResetEvent(true);
![Page 55: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/55.jpg)
Copyright 2006 Thomas P. Skinner
55
FliFlop Example with Synchronization
static AutoResetEvent flopE = new AutoResetEvent(false);
static void Main(string[] args)
{
Thread flip = new Thread(new ThreadStart(flipT));
Thread flop = new Thread(new ThreadStart(flopT));
flip.Start();
flop.Start();
flip.Join();
flop.Join();
Console.WriteLine("Finished");
}
![Page 56: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/56.jpg)
Copyright 2006 Thomas P. Skinner
56
FliFlop Example with Synchronization
static void flipT()
{
for(int i=0;i<5;++i)
{
flipE.WaitOne();
Console.WriteLine("Flip");
flopE.Set();
}
}
![Page 57: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/57.jpg)
Copyright 2006 Thomas P. Skinner
57
FliFlop Example with Synchronization
static void flopT()
{
for (int i = 0; i < 5; ++i)
{
flopE.WaitOne();
Console.WriteLine("Flop");
flipE.Set();
}
}
}
}
![Page 58: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/58.jpg)
Copyright 2006 Thomas P. Skinner 58
Output
![Page 59: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/59.jpg)
Copyright 2006 Thomas P. Skinner 59
Thread Priorities
• A threads scheduling priority can be set.
• The Priority property can be set to:– Highest – AboveNormal – Normal (default)– BelowNormal – Lowest
![Page 60: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/60.jpg)
Copyright 2006 Thomas P. Skinner 60
Terminating a Thread (Aborting)
• A thread can be forcefully terminated by using the Thread.Abort method.
• Aborting a thread is not always a clean approach.
• Things like database connections may not be closed.
• Use finally blocks to ensure releasing these resources.
• Beware a bug discussed in the Prosise book (page 670).
![Page 61: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/61.jpg)
Copyright 2006 Thomas P. Skinner 61
Reader/Writer Locks
• The FCL includes a special lock that allows concurrent reading and mutually exclusive writing.
• AcquireReaderLock and AcquireWriterLock are the essential methods.
• Otherwise this class works similarly to a Monitor.
![Page 62: Chapter 13 Working with Threads. Copyright 2006 Thomas P. Skinner2 Other Reference The book Programming Microsoft.NET by Jeff Prosise. Chapter 14 is excellent.](https://reader030.fdocuments.net/reader030/viewer/2022032708/56649e725503460f94b70c76/html5/thumbnails/62.jpg)
Copyright 2006 Thomas P. Skinner 62
Mutexes
• Mutexes are similar to monitors except that they can span processes.
• To do this we give the mutex a name that can be used by more than one application.
• I am not going to cover this.
• I don’t feel it has use except for very advanced applications. Use a Monitor (lock) instead.