前不久做了一個winform的項目,在項目中涉及了大量的線程操作(也會有異步調用),在處理這些 線程操作的時候不得不做大量的測試、優化,而且還容易出問題,而且還設計很多的界面控件的屬性控 制,搞的我非常的頭疼。用異步線程來做的話,不安全,還容易產生死鎖,雖然.net提供了線程類,可 是當在線程中一旦涉及有Thread.Sleep()操作的時候,原來的線程就會被注入,進而導致界面不能夠被 更新。為了解決這個問題,我查閱了相關的資料,且聽風吟寫的不錯的一篇文章《c#中使用多線程訪問 winform中控件的若干問題》對我起到了一些幫助,可是隨之而來的問題就是,編碼量特別的大,如果按 照且聽風吟的文章提供的方法,我寫這個程序寫的非常的辛苦,雖然解決了Thread.Sleep()的問題,但 是卻不能保證是線程安全的。為什麼這麼說,雖然.net提供了線程類,可是如果沒有深厚的積累,豐富 的經驗,是不能把復雜的線程處理好的。直到今天,我才發現原來.net2.0已經提供了backgroundWorker 組件,使用它就可以很容易的寫出線程安全的軟件來。
有關它的介紹,大家可以參考《VS2005中BackgroundWorker組件的使用經驗》
以下是我做的一個demo,比較簡單,代碼如下:
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Drawing;
using System.Threading;
using System.Windows.Forms;
using System.Xml;
namespace UseBackgroundWorker
{
public partial class Form1 : Form
{
private XmlDocument document = null;
public Form1()
{
InitializeComponent();
}
private void dowloadButton_Click(object sender, EventArgs e)
{
this.backgroundWorker1.RunWorkerAsync();
this.dowloadButton.Enabled = false;
while (this.backgroundWorker1.IsBusy)
{
Application.DoEvents();
}
this.dowloadButton.Enabled = true;
}
private void backgroundWorker1_DoWork(object sender, DoWorkEventArgs e)
{
document = new XmlDocument();
document.Load(@"http://www.tailspintoys.com/sample.xml");
Thread.Sleep(5000);
}
private void backgroundWorker1_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
{
if (e.Error == null)
{
MessageBox.Show(document.InnerXml, "Download Complete");
}
else
{
MessageBox.Show(
"Failed to download file",
"Download failed",
MessageBoxButtons.OK,
MessageBoxIcon.Error);
}
}
}
}
backgroundWorker組件是.net2.0開始提供的組件,也是微軟推薦大家使用的組件,通過它,我們不 難發現,原來編寫一個線程安全的程序是如此的簡單。
出處:http://wlb.cnblogs.com/