您好,登錄后才能下訂單哦!
.Net組件程序設(shè)計(jì)之線程、并發(fā)管理(一)
現(xiàn)在幾乎所有的應(yīng)用程序都是多線程的,給用戶看來就是一個應(yīng)用程序界面(應(yīng)用程序線程),不管什么操作都不會導(dǎo)致界面出現(xiàn)響應(yīng)慢的情況,這些都是多線程的功勞,有了多線程,可以讓應(yīng)用程序盡最大可能的處理更多的操作,調(diào)動很多線程來并行處理請求,這樣會使得應(yīng)用程序有更大的系統(tǒng)吞吐量。
1.1線程
線程是什么呢?線程就是進(jìn)程中的一條執(zhí)行路徑,每個應(yīng)用程序至少在一個線程上運(yùn)行。在本篇中將會對線程稍作講解.
在.NET中,線程是執(zhí)行的基本單元。在.NET中的線程并非是操作系統(tǒng)中的物理線程,而是對物理線程的托管代碼表示。
在.NET System.Threading命名空間下,有個Thread類型的類,它就是代表著托管線程。
1.2線程的創(chuàng)建
我們直接來看下線程創(chuàng)建的示例:
1 public class ThreadingMethodCase 2 { 3 public static void ThreadingMethod() 4 { 5 Thread thread = Thread.CurrentThread; 6 int threadid = thread.ManagedThreadId; 7 Console.WriteLine(thread.Name + "ThreadID is " + threadid); 8 } 9 }
1 ThreadStart threadstart = new ThreadStart(ThreadingMethodCase.ThreadingMethod); 2 Thread thread = new Thread(threadstart); 3 thread.Name = "SubThread"; 4 thread.Start();
在.NET中創(chuàng)建一個線程首先需要線程方法,什么叫線程方法?首先線程是一個操作或是一組操作的表示,線程方法就是前面這句話中的【操作】。
這里先看一下Thread類型的構(gòu)造函數(shù)接受了一個ThreadStart類型的無參數(shù)委托,這個是好理解的。
線程創(chuàng)建了必須要顯示的調(diào)用它的Start()函數(shù)才能開始執(zhí)行線程。調(diào)用Strat()函數(shù)是不會對當(dāng)前線程造成阻塞的,就是說在調(diào)用了之后控制權(quán)會立刻的回到當(dāng)前的線程的客戶端中。
1 public sealed class Thread 2 { 3 public void Suspend(); 4 public void Resume(); 5 …… 6 }
Suspend()方法是掛起線程的執(zhí)行.
Resume()方法則是釋放掛起的線程,讓線程繼續(xù)執(zhí)行在調(diào)用Suspend()方法的時候,是不會造成當(dāng)前線程阻塞的,在調(diào)用后,控制權(quán)立即返回的,而且在要被掛起的線程中, 也不是被立即掛起的,而是在執(zhí)行到一個安全點(diǎn)的時候,才會執(zhí)行掛機(jī)操作的。什么是安全點(diǎn)?舉個例子吧,假如要被掛起的線程中 正在執(zhí)行一個函數(shù)的時候,外部被通知命令,要被掛起,這個時候線程是不會被掛起的,當(dāng)這個函數(shù)執(zhí)行完畢的時候,線程則會被掛起, 假設(shè)編輯器是把安全點(diǎn)插設(shè)在每個函數(shù)的末端的。
.NET中是不推薦我們使用這兩個函數(shù)的,因?yàn)闀斐珊芏喾矫娴牟环€(wěn)定。
1.3.2線程睡眠
1 public sealed class Thread 2 { 3 public static void Sleep(int millisecondsTimeout); 4 public static void Sleep(TimeSpan timeout); 5 …… 6 }
Sleep()是靜態(tài)函數(shù),是一個阻塞調(diào)用并且使當(dāng)前線程放棄CPU時間片,就是在休眠指定的時間后,控制權(quán)才會返回到調(diào)用的線程。
Thread.Sleep(20);//讓當(dāng)前調(diào)用線程休眠20毫秒
Thread類還提供了另一種類似于休眠的操作:
1 public static void SpinWait(int iterations);
調(diào)用SpinWait()也是會造成當(dāng)前阻塞的,但是當(dāng)前線程不會放棄CPU時間片,而是在等待有限的時間(參數(shù)設(shè)置)后繼續(xù)執(zhí)行, 這種函數(shù)是在可控的情況下才去這樣調(diào)用的,比如說當(dāng)前線程要使用一個資源,而這個資源在被其他線程使用,那么就可以使用 SpinWait()函數(shù),在等待有限的時間后,再去讀取資源,如果資源還沒被其他線程釋放,當(dāng)前線程也會繼續(xù)執(zhí)行,所有這是用于可控的情況下的方法。
1.3.3 加入線程
Thread類的Join()方法可以讓一個線程等待另一個線程的終結(jié)。
這句定義什么意思呢?說是說不清的,來看一下Thread.Join()示例代碼 :
1 public class StudyCase 2 { 3 public void ThreadingTest() 4 { 5 ThreadStart threadstart = new ThreadStart(ThreadingMethodCase.ThreadingMethod); 6 Thread thread = new Thread(threadstart); 7 thread.Name = "newThread"; 8 Thread.CurrentThread.Name = "CurrentThread"; 9 for (int i = 0; i < 5; i++) 10 { 11 if (i == 0) 12 { 13 thread.Start(); 14 thread.Join(); 15 } 16 Console.WriteLine(Thread.CurrentThread.Name+"_"+i.ToString()); 17 } 18 } 19 20 }
1 public class ThreadingMethodCase 2 { 3 public static void ThreadingMethod() 4 { 5 Thread thread = Thread.CurrentThread; 6 int threadid = thread.ManagedThreadId; 7 Console.WriteLine(thread.Name + "ThreadID is " + threadid); 8 } 9 }
從上圖的結(jié)果再結(jié)合代碼看一下,就大概的清楚了Join的意思了,意義就是阻塞當(dāng)前線程,等待子線程(ThreadingTest函數(shù)中的thread變量)執(zhí)行完畢時,當(dāng)前線程再執(zhí)行。
1.3.4線程中止
調(diào)用Thread類型提供的Abort()方法可以中止線程的運(yùn)行,并且被中止的線程會拋出一個ThreadAbortException類型的異常。下面的示例代碼會清晰的描述和示例代碼結(jié)果圖。
來看示例代碼:
1 public class ThreadingMethodCase 2 { 3 public static void ThreadingMethodDiv() 4 { 5 try 6 { 7 while (true) 8 { 9 Console.WriteLine("測試子線程中止"); 10 } 11 } 12 catch (ThreadAbortException abex) 13 { 14 Console.WriteLine(Thread.CurrentThread.Name+"-子線程內(nèi)部-" + abex.Message); 15 } 16 } 17 } 18 public class StudyCase 19 { 20 public void ThreadingTestAbort() 21 { 22 Thread.CurrentThread.Name="CurrentThread"; 23 ThreadStart threadstart = new ThreadStart(ThreadingMethodCase.ThreadingMethod); 24 Thread thread = new Thread(threadstart); 25 thread.Name = "newThread"; 26 27 thread.Start(); 28 for (int i = 0; i < 10; i++) 29 { 30 Console.WriteLine(i.ToString()); 31 } 32 thread.Abort(); 33 thread.Join(); 34 35 Console.WriteLine("當(dāng)前線程"); 36 } 37 38 }
將在下一章講解線程同步。
免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場,如果涉及侵權(quán)請聯(lián)系站長郵箱:is@yisu.com進(jìn)行舉報,并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。