C#在不同线程的同一类中的父线程中调用方法

Posted

技术标签:

【中文标题】C#在不同线程的同一类中的父线程中调用方法【英文标题】:C# Call method in parent thread in same class in different thread 【发布时间】:2018-07-14 02:25:23 【问题描述】:

我有一个问题。在一个表单中,我在一个单独的类的线程中调用函数:

public partial class mainForm : Form

  private void button_Click(object sender, EventArgs e)
            
    myclass myc = new myclass();
    Thread mythread = new Thread(myc.mainfunction);
    mythread.name ="A";
    mythread.Start();
   

在这个函数中,线程“A”中的“mainfunction”在同一类的函数上生成了一个附加线程。

现在这个子线程应该访问同一个类的父线程“A”的一个函数。

我知道这如何与表单中的委托一起访问控件。但在这种情况下不是。谁能帮帮我?

class myclass


    public void mainfunction ()
    
      ...
      myclass submc = new myclass();
      Thread subthread = new Thread(new ParameterizedThreadStart(submc.subfunction));
      mythread.name ="B";
      subthread.Start(this);
    

    public void subfunction(object parm)
    
      myclass parentc = (myclass)parm;
      parentc.doanything()

    

    public void doanything()
    
     ...
     // this should happen in Thread A NOT B
    




提前致谢。

干杯

【问题讨论】:

线程 A 将不再存在。它已完成运行并终止。为什么你需要在那个特定的线程上运行一些东西? 好像XY problem 嗨,哦,是的。不知何故,我没有得到它。线程已完成...所以原因是“doanything()”方法中的 tableadapter 更新。我有时会收到 System.Data.OleDb.OleDbException 并且不知道为什么会发生这种情况。想要将表格上的更新整合到一个线程中。 【参考方案1】:

尝试使用 System.Reactive 中的 EventLoopScheduler。 一个例子:

class Program

    static void Main(string[] args)
    
        var scheduler = new EventLoopScheduler(); // will manage thread A
        WriteThreadName();
        scheduler.Schedule(WriteThreadName);
        scheduler.Schedule(() =>
        
            // inside thread A we create thread B
            new Thread(() =>
            
                WriteThreadName();
                scheduler.Schedule(WriteThreadName); // schedule method on thread A from thread B
            ).Start();
        );

        Console.ReadLine();

    

    static void WriteThreadName()
    
        Console.WriteLine("Thread: "+Thread.CurrentThread.ManagedThreadId);
    

打印出来

Thread: 9
Thread: 11
Thread: 12
Thread: 11

【讨论】:

【参考方案2】:

通常,您不需要让另一个线程执行某些代码,您只需要使用锁暂停其他线程。在这种情况下,为什么要在线程 A 中执行代码会很有趣。(Winforms 只需要在其他线程中运行代码,因为它可以使用 COM 组件,它不能很好地处理多线程。)

对于您的线程 A,这是不可能的,因为当执行到达 main 方法的末尾时它可能已经死了。

Windows 窗体使用“调度程序”概念:有一个主循环,它运行直到您的程序关闭,并在通过 Control.Invoke 插入工作包时在其线程中执行工作包。您也可以在 mainfunction() 的末尾添加这样一个几乎无限循环,从 List 执行 Action-Delegates (https://msdn.microsoft.com/en-us/library/system.action(v=vs.110).aspx) - 使用 ConcurrentList 或不要忘记在插入/删除元素时锁定(例如列表) .

您也可以尝试使用预定义的 Dispatcher:https://msdn.microsoft.com/en-us/library/system.windows.threading.dispatcher.aspx

但也许,在这种情况下,另一种不切换线程的解决方案可能会更好。

【讨论】:

以上是关于C#在不同线程的同一类中的父线程中调用方法的主要内容,如果未能解决你的问题,请参考以下文章

在C#的同一个异步线程中运行不同的任务[重复]

C# 多线程 ,可以多个线程做一任务,并且提高做任务的效率吗

C# 线程

C# 异步方法加await调用不就变成同步方法了吗

同一个类中,有两个方法都用 synchronized 修饰,这两个方法线程安全吗?

如何在C#中,在一个类里调用另外一个类的方法