轉帖|其它|編輯:郝浩|2011-03-11 10:37:41.000|閱讀 878 次
概述:在項目中時常會運行很多極其復雜的算法之后再更新UI控件,可是我們發現這會耗費大量的時間,幾乎讓UI進程假死。有什么辦法可以讓程序在后臺完成這些復雜的算法,當算法完成的時候再去更新UI控件以避免UI進程假死的情況呢?對了,多線程技術!后臺創建一個線程來進行復雜計算,就可以不耽誤UI線程更新 UI控件。
# 界面/圖表報表/文檔/IDE等千款熱門軟控件火熱銷售中 >>
在項目中時常會運行很多極其復雜的算法之后再更新UI控件,可是我們發現這會耗費大量的時間,幾乎讓UI進程假死。有什么辦法可以讓程序在后臺完成這些復雜的算法,當算法完成的時候再去更新UI控件以避免UI進程假死的情況呢?對了,多線程技術!后臺創建一個線程來進行復雜計算,就可以不耽誤UI線程更新UI控件??墒侨绻苯釉诰€程執行的函數里面去更新UI控件則會報“跨線程訪問無效”的錯誤提示。下例中前臺XAML文件里有兩個UI控件label1和label2,在這里通過調用this.label1.Dispatcher.BeginInvoke方法執行labelInvoke委托的函數UpdateLabel(string content),在UpdateLabel函數里面就可以直接更新lable1控件需要顯示的內容,同理可以更新其他的UI控件的顯示。
下面我們看一下如何在自創建的后臺線程里面更新UI線程的label1控件:
#region 啟動一個無參數的只負責更新UI線程的自定義后臺線程
public void NoParamThread()
{
Thread thread = new Thread(ShowStr);
thread.IsBackground = true;
thread.Start();
}
/// <summary>
/// 顯示Str的函數
/// </summary>
public void ShowStr()
{
string content= "無參數傳遞的線程更新";
//運行labelInvoke委托的方法UpdateLabel,并且傳遞參數content
this.label1.Dispatcher.BeginInvoke(new labelInvoke(UpdateLabel),content);
}
/// <summary>
/// 更新Label的委托
/// </summary>
/// <param name="content"></param>
public delegate void labelInvoke(string content);
/// <summary>
/// 更新label1的方法
/// </summary>
/// <param name="content"></param>
public void UpdateLabel(string content)
{
//更新UI線程上的 this.label1.Content值
this.label1.Content = content;
}
#endregion
某一個函數運行需要2秒,輸入5種不同的參數得到5個結果,那么一個線程來做這個事需要10秒??勺鲆粋€循環同時開5個線程運算這個函數并且帶入參數,那么一共只需要2秒即可,這就是后臺的多線程并行任務。
下面請看如何來創建多個線程執行并行任務。首先循環創建5個線程,再為每個線程傳入一個參數,但直接創建線程是無法傳遞參數的!這些參數如何傳輸進入線程執行的函數內部呢?在這里我們使用Thread thread = new Thread(new ParameterizedThreadStart(ShowString));的ParameterizedThreadStart對象來傳遞如參數。這樣在線程的實例中運行thread.Start(object obj)重載函數即可傳遞一個參數。
#region 啟動傳遞一個參數的進程
public void HaveParamThread(string str)
{
//循環創建5個線程
for (int i = 0; i < 5; i++)
{
Thread thread = new Thread(new ParameterizedThreadStart(ShowString));
thread.IsBackground = true;
thread.Start(str + i.ToString());
}
}
/// <summary>
/// 顯示Str的函數
/// </summary>
public void ShowString(object content)
{
string con = content as string;
//做復雜運算
string strcon = con.Substring(0, con.Length - 2);
//運行labelInvoke委托的方法labelDelegete,并且傳遞參數con
this.label2.Dispatcher.BeginInvoke(new labelDelegete(UpdateLab), con);
}
/// <summary>
/// 更新Label2的委托
/// </summary>
/// <param name="content"></param>
public delegate void labelDelegete(string content);
/// <summary>
/// 更新label2的方法
/// </summary>
/// <param name="content"></param>
public void UpdateLab(string content)
{
//更新UI線程上的 this.label1.Content值
this.label2.Content =this.label2.Content+ "--"+ content;
}
#endregion
通過上面的實例,我們可以總結出在Silverlight中多線程技術通常用于以下兩個方面。
第一、加快UI控件響應,提高用戶體驗。通過UI線程和后臺計算線程的分離,后臺線程專注于計算, 計算完畢將結果推給前臺UI線程顯示出來。
第二、后臺多任務并行運算。同時開多個線程運行不同參數的一個復雜計算函數以節約計算時間。
本實例采用VS2010+Silverlight 4.0編寫。
本站文章除注明轉載外,均為本站原創或翻譯。歡迎任何形式的轉載,但請務必注明出處、不得修改原文相關鏈接,如果存在內容上的異議請郵件反饋至chenjj@fc6vip.cn
文章轉載自:網絡轉載