【问题标题】:Thread-safe update TextBox from another class从另一个类进行线程安全更新 TextBox
【发布时间】:2015-02-18 04:37:13
【问题描述】:

我有一个名为“Home”的表单和一个名为“Server”的类,它是线程化的。 Home 有一个文本框,我想在服务器中发生事情时附加它。附加不在同一类中的文本框的最简单的线程安全方法是什么?我看到很多关于这个主题的讨论,但似乎没有什么能回答我的问题。其他解决方案还包含许多看似简单的代码。

我这样开始我的线程表单 Home:

public void StartThread()
{
    Server s = new Server();
    Thread t = new Thread(s.DoWork);
    t.Start();
}

class Server
{
    public void DoWork()
    {
        while (!_shouldStop)
        {
            StartServer();
        }
    }

    public void RequestStop()
    {
        _shouldStop = true;
    }

    private volatile bool _shouldStop;

    internal void StartServer()
    {
        try
        {
        // Server Stuff
        // Something happens here and I want to append a string to the text box in Home.
        }

        catch (Exception)
        {
            //Exception, append text box with some other string.
        }
    }

【问题讨论】:

  • 你到底为什么要忙着等待线程完成呢?这违背了启动另一个线程的全部目的。
  • 还有一些其他的等待条件。只是没有把它和其他人一起剪掉。
  • 它仍然不应该存在。它根本不应该等待。
  • 我有我的理由。这和这个问题有什么关系?
  • 我只是告诉你这是一个非常糟糕的主意,而且几乎肯定会给你带来麻烦。无论您尝试做什么,都应该异步执行,而不是等待线程完成。如果你真的必须等待(最终不会是这样),那么至少你不应该在线程上忙着等待。

标签: c# multithreading winforms


【解决方案1】:
  1. 让表单创建一个Progress<string> 实例,
  2. 将处理程序附加到适当更新 UI 的进度更改事件。
  3. 让工作人员接受它报告进度的IProgress<string> 实例。

Progress 类将处理将代码编组到 UI 线程。

这确保了 UI 与非 UI 代码的正确分离。

【讨论】:

    【解决方案2】:

    我不确定这是否是您的意思(我假设执行跨线程操作?)但是...

    textBox1.Invoke(new MethodInvoker(delegate { textBox1.AppendText("Hi"); }));
    

    这将安全地将一些文本附加到您的文本框,您只需添加 if 语句等。

    【讨论】:

      猜你喜欢
      • 2012-04-27
      • 1970-01-01
      • 2013-03-16
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多