Thread完成运行后运行函数

时间:2017-02-10 15:11:40

标签: c# multithreading process

我正在尝试在线程完成运行后运行一个函数。当按下UI按钮并且线程需要一段时间才能完成时,我的线程开始 一旦完成运行,我想调用一个函数。这是我到目前为止尝试的代码。当我尝试运行我的代码时,线程永远不会执行,应用程序冻结。关于如何解决这个问题的任何建议都会有所帮助。

public bool StartProbe()
{
    if (File.Exists(Path.Combine(ObsProbeFolder, "probePJM.exe")))
    {
        ThreadStart ProbeThreadStart = new ThreadStart(() =>
        // right side of lambda    
            {
               // does stuff
            });

            ProbeThread = new Thread(ProbeThreadStart);
            ProbeThread.Priority = ThreadPriority.BelowNormal;
            ProbeThread.SetApartmentState(ApartmentState.STA);
            ProbeThread.Start();

    }
    else
    {                      
        return false;
    }

    // waiting for thread to finish 
    ProbeThread.Join();
    // run a function
    loadData();

    return true;
} 

2 个答案:

答案 0 :(得分:0)

我会使用BackgroundWorker:

Worker = new BackgroundWorker();
            Worker.RunWorkerCompleted += Worker_RunWorkerCompleted;
            Worker.DoWork += Worker_DoWork;

            Worker.RunWorkerAsync(new BackgroundArguments()
            {
                // arguments
            });

在备用线程上工作:

private void Worker_DoWork(object sender, DoWorkEventArgs e)
{       
    // do stuff
}

返回UI线程:

private void Worker_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
    {
       // load data or whatever on UI thread
    }

答案 1 :(得分:0)

不要使用BackgroundWorker - 这是一个非常古老的课程,我希望有一天它会被MS称为过时的课程。

正如你所说,你有一个按钮,为即发即弃场景创建一个async void事件处理程序。当您检查一些exe文件时,我假设您正在运行一些Process in background。此外,您不需要一个线程来运行您的流程 - 您正在加入它,这就是UI挂起的原因。

private async void button_Click(object sender, EventArgs e)
{
    // wait for a result from outer process
    var result = await RunProcessInBackGround();
    //do whatever you need in the UI-context
    loadData(result);
}

// T is a type of the result, should be changed
private async Task<T> RunProcessInBackGround()
{
    var tcs = new TaskCompletionSource<T>();
    // run your process
    var process  new Process {/* your params here */};
    process.Exited += (sender, args) =>
        {
            // here your process has already done his job
            tcs.SetResult(result);
            process.Dispose();
        };
    // process will start as a separate process, no need to create a thread to wait for it
    process.Start();
    // return the task which will be awaited for
    return tcs.Task;
}