簡體   English   中英

Windows窗體C#中的多線程

[英]Multithreading in windows forms C#

在Windows應用程序中,除主線程外,還有另一個線程每分鍾進行一次長時間運行操作,並使用Invoke方法更新UI。

當另一個線程處於睡眠狀態時,我們如何優雅地終止它?

在這里使用睡眠是正確的選擇嗎?

而不是先創建線程然后終止,而是使用表單計時器每60000毫秒觸發一個后台工作線程? 然后,您根本不需要休眠后台線程。

這意味着您只需要停止計時器即可停止生成更多后台任務,但是顯然這不會停止任何當前活動的后台線程。

線程應該很少被中止,因為沒有任何強大的機制可以實現任何一致性。 有各種保護措施,例如關鍵代碼標記。 但是,我認為最好將長期運行的代碼輪詢以進行取消,然后可以編寫自己的邏輯以放棄船艦並提早返回。 注意 ,這與強行中止線程不同。

我認為在任何情況下睡眠都不是正確的選擇。

例如:

private bool _askedToCancel;

public void lonRunThread()
{
    if (!_askedToCancel)
    {
        Operation1();
        Invoke(new UpdateDelegate(updateState));
    }

    if (!_askedToCancel)
    {    
        Operation2();
        Invoke(new UpdateDelegate(updateState));
    }
}

似乎有些混亂,但是,如果您拒絕強行中止線程,而是使用取消方法,則可以很好地控制執行的邏輯。

因為這不是關鍵代碼,並且因為對布爾值的操作是原子性的,所以兩個線程在不進行任何鎖定的情況下與bool進行通信應該是安全的。 即使不是真正安全,唯一的結果就是要做更多的工作。

您始終可以將線程設置為后台線程,這樣,當應用程序退出時,該線程將自動停止。

您何時希望停止線程?

如果您希望它在操作過程中停止,則布爾標志將是適當的。

所以代替

while(true)

你會做類似的事情

while(exit == false)

我會在longRunThread方法中更改while(true)並使其

while (_RunLongThread)

然后在TestForm中,我將聲明私有布爾值_RunLongThread = true並將其從需要停止長時間運行的線程的任何方法設置為false。

那是停止它的“優美”方式,即等待完成其當前任務然后終止

沒有諸如正常線程終止之類的東西。 相反,應該指示您的線程在不再需要時停止執行其工作。 您可以通過創建類來保存工作線程參數來實現此目的,在該線程中存儲是否應停止工作的信息,並將該類的對象傳遞給線程。

public class WorkerParams
{
    public bool Stop = false;
}

private void TestForm_Load(object sender, EventArgs e)
{
    _thread = new Thread(lonRunThread);
    _thread.Start(new WorkerParams());
}

public void lonRunThread(object argument)
{
    WorkerParams param = argument as WorkerParams;
    DateTime lastExec = DateTime.MinValue;
    while(!param.Stop)
    {
        if (new TimeSpan(DateTime.Now.Ticks - lastExec.Ticks).TotalSeconds >= 60)
        {
            Operation1();
            Invoke(new UpdateDelegate(updateState));
            Operation2();
            Invoke(new UpdateDelegate(updateState));
            lastExec = DateTime.Now;
        }
        Thread.Sleep(500);
    }
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM