C# 通过C中的线程调用其他类的事件#

C# 通过C中的线程调用其他类的事件#,c#,.net-3.5,C#,.net 3.5,情况如下: 我有一个创建主窗体的类。它将主窗体的已创建对象保持为静态成员,如下所示: public static mainAppWnd; mainAppWnd = new MainAppWnd(); public static void Listen() { NamedPipeServerStream server = new NamedPipeServerStream("49A252BB-C0FC-4bdb-8CA7-522A3BAE3432"); server.WaitF

情况如下:

我有一个创建主窗体的类。它将主窗体的已创建对象保持为静态成员,如下所示:

public static mainAppWnd;
mainAppWnd = new MainAppWnd();
public static void Listen()
{
    NamedPipeServerStream server = new NamedPipeServerStream("49A252BB-C0FC-4bdb-8CA7-522A3BAE3432");
    server.WaitForConnection();

    byte[] buffer = new byte[1000];
    int bytesread = server.Read(buffer, 0, 1000);

    string args = Encoding.UTF8.GetString(buffer, 0, bytesread - 1);
    args.Trim();
    string[] arrArgs = args.Split(' ');
    mainAppWnd.LaunchNewForm(arrArgs.ToList()); //This line crashes because of a UI Call across threads.
}
表单是在
main
代码中的某个地方创建的,如下所示:

public static mainAppWnd;
mainAppWnd = new MainAppWnd();
public static void Listen()
{
    NamedPipeServerStream server = new NamedPipeServerStream("49A252BB-C0FC-4bdb-8CA7-522A3BAE3432");
    server.WaitForConnection();

    byte[] buffer = new byte[1000];
    int bytesread = server.Read(buffer, 0, 1000);

    string args = Encoding.UTF8.GetString(buffer, 0, bytesread - 1);
    args.Trim();
    string[] arrArgs = args.Split(' ');
    mainAppWnd.LaunchNewForm(arrArgs.ToList()); //This line crashes because of a UI Call across threads.
}
现在,我一次只需要打开这个应用程序的一个实例,我是通过互斥来实现的。那部分很好用。当该应用程序的第二个实例打开时,我必须检查它是否包含一些命令行参数。如果是这样,我必须将这些命令行参数传递给现有的运行实例,并且在该运行实例中,我必须打开一个新表单。此新表单的打开将在
MainAppWnd
类中处理。为了做到这一点,我使用了管道,并在线程中使用了
Listen
。我的线程函数如下所示:

public static mainAppWnd;
mainAppWnd = new MainAppWnd();
public static void Listen()
{
    NamedPipeServerStream server = new NamedPipeServerStream("49A252BB-C0FC-4bdb-8CA7-522A3BAE3432");
    server.WaitForConnection();

    byte[] buffer = new byte[1000];
    int bytesread = server.Read(buffer, 0, 1000);

    string args = Encoding.UTF8.GetString(buffer, 0, bytesread - 1);
    args.Trim();
    string[] arrArgs = args.Split(' ');
    mainAppWnd.LaunchNewForm(arrArgs.ToList()); //This line crashes because of a UI Call across threads.
}

在上面的代码中,最后一行由于跨线程的UI调用而崩溃。现在,我明白了我必须以某种方式异步地将消息传递给MainAppWnd,以便在它自己的预先存在的上下文中启动这个新表单,但我无法这样做。如果它是C++,我就简单地做了一个<代码>::PASSMEMSEAGE()/CUT>,它会起作用,但是在C语言中,最简单的方法是什么?< /P> < P>假设这是Windows窗体,并且<代码> MIMAPWND < /C> >是<代码>表单< /C>或类似的,可以使用:

Action action = () => mainAppWnd.LaunchNewForm(arrArgs.ToList());
mainAppWnd.BeginInvoke(action);

和用于在与调用它们的控件关联的UI线程上执行委托。两者之间的区别在于
BeginInvoke
是异步的(启动并忘记),而
Invoke
在委托执行之前一直阻塞。

非常感谢。召唤和开始召唤对我来说很清楚。你能解释一下“()=>mainAppWnd.LaunchNewForm(arrArgs.ToList());”背后的魔力吗有一点吗?@Aamir:这只是一个lambda表达式-一种创建委托的简单方法,无需编写完整的单独方法。谢谢。那我就回到你的书上来:)