背景
我是一个非常擅长在C#中进行线程/并发操作的人,我正在努力使用跨线程的GUI应用程序。现在我遇到了在运行时被抛出的异常,我不知道如何处理。首先,我将提供正在发生的事情的背景,然后我将描述我试图调试的内容。
我有一项任务可以进行大量计算。
// display dump information
displayDumpTask = readingDumpTask.ContinueWith(
delegate
{
Parallel.Invoke
(
() => this.DisplayEntries(),
() => this.DisplayDump()
);
}
, TaskScheduler.FromCurrentSynchronizationContext());
完成此任务后,我想一次做两件事。我按照以下方式实施这个过程......
private void DisplayEntries()
{
UpdateUIDelegate myDel = new UpdateUIDelegate(this.DisplayEntries);
if (this.InvokeRequired)
{
this.BeginInvoke(myDel);
}
// fills some data into labels on the GUI
}
正在委派的两种方法,按以下方式工作......
方法#1
private void DisplayDump()
{
UpdateUIDelegate myDel = new UpdateUIDelegate(this.DisplayDump);
if (this.InvokeRequired)
{
this.BeginInvoke(myDel);
}
// fills some data into a RTB on the GUI
}
方法#2
InvalidOperationException
我想说清楚方法#1没有使用方法#1所使用的任何控件。
问题陈述
这里的问题是,一旦我尝试从DisplayDump
函数内部访问控件,我就会得到DisplayDump
。当我点击转储标签时,我只会遇到此异常,如下所示。
我认为这与DisplayDump
方法正在访问位于转储标签内的文本框这一事实有关。现在,当我在导航标签上时,我从未遇到任何问题,一切都安然无恙。
尝试调试
我今天早上才发现如何看到并行任务调试窗口,更别说真的知道如何使用它来解决我的问题了。所以,我已经从 Parallel.Invoke 块中删除了一个方法调用,我发现在哪个选项卡上无关紧要,在这种情况下我永远不会得到异常({{ 1}}总是有效的)。但是,只要我在Parallel
语句中有两个操作,就会出现问题。所以...到目前为止,我所知道的是它与Parallel.Invoke
。
答案 0 :(得分:0)
调用BeginInvoke后,您的方法应该返回。如果你没有返回,那么将在非UI线程上访问GUI,你将获得InvalidOperationException。
private void DisplayEntries()
{
UpdateUIDelegate myDel = new UpdateUIDelegate(this.DisplayEntries);
if (this.InvokeRequired)
{
this.BeginInvoke(myDel);
return; // ** change here
}
// fills some data into labels on the GUI
}