【问题标题】:C# BackgroundWorker and InvokeC# BackgroundWorker 和调用
【发布时间】:2015-02-17 08:27:30
【问题描述】:

谁能解释为什么从BackgroundWorker 调用Thread.Sleep 会阻止其执行。调用应使委托在 UI 线程上执行,而后台线程应继续执行。但这不会发生 - 为什么?

public partial class Form1 : Form
{
    public Form1()
    {
        InitializeComponent();
        BackgroundWorker bgrw = new BackgroundWorker();
        bgrw.DoWork += new DoWorkEventHandler(bgrw_DoWork);

        bgrw.RunWorkerAsync();
    }

    void bgrw_DoWork(object sender, DoWorkEventArgs e)
    {
        Console.WriteLine(DateTime.Now);
        this.Invoke(new Action(() => { Thread.Sleep(2000); })); //should be executed on the UI thread
        Console.WriteLine(DateTime.Now); // This line is executed after 2 seconds
    }       
}

【问题讨论】:

  • “调用应该导致委托在 UI 线程上执行” - 是 - “并且后台线程应该继续” - 不。查看Invoke 的定义并注意它的返回值是委托返回的值。在代码完成执行之前,它无法将该值返回给您。 Invoke 块。
  • 为什么不在您启动 Backgroundworker 后立即从 UI 线程调用 Thread.Sleep() ?

标签: c# .net multithreading backgroundworker invoke


【解决方案1】:

这是一个相当简单的解释。 Invoke 是一个阻塞调用。如果您想在 UI 消息循环上异步排队工作,请改用 BeginInvoke

异步在线程上执行指定的委托 控件的底层句柄创建于。

void bgrw_DoWork(object sender, DoWorkEventArgs e)
{
    Console.WriteLine(DateTime.Now);
    this.BeginInvoke(new Action(() => { Thread.Sleep(2000); })); 
    Console.WriteLine(DateTime.Now);
}  

请注意您的代码,因为当前构造的代码没有意义。我假设您将其用于测试目的。

【讨论】:

    猜你喜欢
    • 2018-03-18
    • 2018-06-25
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2010-12-01
    • 2020-11-20
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多