winform防止介面卡死的三種方法
阿新 • • 發佈:2019-01-31
在程式設計過程中經常會遇到耗時操作,這個時候如果不採取一些必要的非同步操作,就會導致介面的卡死,這裡以winform為例子,介紹三種方法防止介面卡死,對這幾個方法稍加修改同樣適用於wpf,silverlight等程式
首先給出一個函式模擬耗時操作
1使用委託+QueueUserWorkItem
delegate void ChangeInvoke(int num) ;
private void ChangeNum(int num)
{
MessageBox.Show(num.ToString());
}
private void DoSomeThing(object state) { int i=0; for (int i = 0; i < int.MaxValue-1; i++) { i++; } ChangeInvoke change = new ChangeInvoke(ChangeNum); this.Invoke(change,new object[]{i}); }
以下是通過QueueUserWorkItem非同步呼叫
ThreadPool.QueueUserWorkItem(DoSomeThing);
其實很簡單,也就是一句程式碼的事。
2使用Task
首先還是模擬耗時操作
這個耗時操作因為添加了CancellationToken,因而支援取消private int TaskTest(int num,CancellationToken token) { // num = 0; for (int i = 0; i < int.MaxValue-10; i++) { token.ThrowIfCancellationRequested(); num++; } return num; }
接著定義耗時操作完成之後的操作
最後是利用進行非同步操作private void ShowResult(Task<Int32> t) { try { MessageBox.Show(t.Result.ToString()); } catch(AggregateException ex) { MessageBox.Show("操作中斷!"); } }
Task<Int32> task = new Task<Int32>(n=>TaskTest(10,cancelSource.Token),0);
task.Start();
Task tsk = task.ContinueWith(t => ShowResult(t));
如此程式將會在耗時操作結束是呼叫ShowResult函式
以上兩種方法使用到Task 和QueueUserWorkItem,因為之前已經有寫過文章詳細的介紹過,這裡就不細說了,有興趣的可以翻閱本人的前幾篇文章,有做比較詳細的介紹。
3利用APM進行非同步呼叫
依然是耗時操作
private int DoSomeThing(int num)
{
for (int i = 0; i < int.MaxValue - 10; i++)
{
num++;
}
return num;
}
下面是耗時操作結束後的操作
private void APMDone(IAsyncResult result)
{
var sumDelegate = (Func<int, int>)result.AsyncState;
try
{
int sumResult = sumDelegate.EndInvoke(result);
MessageBox.Show(sumResult.ToString());
}
catch(Exception e)
{
MessageBox.Show(e.Message);
}
}
最後是呼叫的方法
Func<int, int> SumDelegate = TaskTest2;
SumDelegate.BeginInvoke(0, APMDone, SumDelegate);
本人才疏學淺,這裡僅僅對這些方法做一個簡單的總結,其內部的原理就不細說了,免得被高手拍磚,如有疏漏之處,還望指出,如果對於你有一定的參考價值,那真是莫大的榮幸