繁体   English   中英

此方法在哪个线程上运行? C#

[英]On what thread does this method runs? C#

我有一个更新数据库记录的方法,并且考虑到以下因素,我想知道此方法是否确实在BackGroundWorker线程中运行:

public partial class Form1 : Form
{
    BackgroundWorker bg = new BackgroundWorker();

    public Form1()
    {
        InitializeComponent();
    }

    private void Form1_Load(object sender, EventArgs e)
    {
       bg.DoWork += new DoWorkEventHandler(bg_DoWork);
       bg.RunWorkerAsync();
    }

    void bg_DoWork(object sender, DoWorkEventArgs e)
    {
        UpdateDatabaseRecords(); // <-- Does this method runs in my BackGroundWorker?
    }

    private void UpdateDatabaseRecords()
    {
        SqlConnection conn = new SqlConnection();
        // etc...
    }
}

如果我直接在bg_DoWork方法内部编码更新内容,是否会有区别?
就像是:

void bg_DoWork(object sender, DoWorkEventArgs e)
{
    SqlConnection conn = new SqlConnection();
    // etc...
    // do the update codes here instead of doing 
    // it by calling another method.
}

是的,它在单独的线程上执行。 不,如果直接将其放在该方法中,就不会有线程差异。

由于函数调用的实现方式,函数在调用它们的线程中运行。 因此,由于您的后台工作程序正在调用bg_DoWork函数,因此它将在工作程序的线程中运行。

由于代码段很小,因此调用另一个函数可能不会有明显的不同。 如果您只是做一点点工作,那么您可以将其全部整合到一个功能中。 如果您开始增加工作者的工作复杂性,那么您可能需要开始将其拆分为许多功能。

不,没有区别。 调用方法会为该方法调用创建一个新的堆栈框架,将其压入当前线程的调用堆栈中,然后将控制权转移给它。 JIT编译器也可以内联该方法,因此您在“手动内联”版本和当前版本之间的反汇编中可能看不到任何区别

顺便说一句,这是来自反射器的BackgroundWorker.RunAsync的代码:

public void RunWorkerAsync()
{
    this.RunWorkerAsync(null);
}

public void RunWorkerAsync(object argument)
{
    if (this.isRunning)
    {
        throw new InvalidOperationException(SR.GetString("BackgroundWorker_WorkerAlreadyRunning"));
    }
    this.isRunning = true;
    this.cancellationPending = false;
    this.asyncOperation = AsyncOperationManager.CreateOperation(null);

    // the important bit
    this.threadStart.BeginInvoke(argument, null, null);
}

如您所见,您的代码将在WorkerThreadStartDelegate.BeginInvoke的上下文中运行。 这应该意味着一个线程池线程将对其进行拾取,您可以通过测试bg_DoWork方法中的Thread.CurrentThread.IsThreadPoolThread的值来进行验证。

是的,它在单独的线程(后台)中运行。 唯一的区别是您无权访问DoWorkEventArgs参数,但可以将其传递给您的方法。

我不这么认为!

将其包装在方法中不会使其在不同的线程中工作,我认为bg_DoWork所有代码bg_DoWork将在后台工作程序上工作(包括UpdateDatabaseRecords方法上的所有代码)。

有一个ThreadSynchronizationContext类,您可以在其中发布方法以在不同的线程上下文上工作。

您可以在bg_DoWork方法和UpdateDatabaseRecords方法中放置一个断点,从而在Visual Studio上测试代码。 从“调试-> Windows->线程”菜单的“线程窗口”中检出它,以检查它是否在主线程或辅助线程上工作。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM