C# 并行编程:Can';无法并行访问UI?
我试图在wpf c#中创建一个函数的并行执行,该函数也在UI上运行操作。但是,当运行UI控件上的方法时,总会出现异常:调用线程无法访问此对象,因为其他线程拥有它。异常总是在正在运行的循环的第二个实例上调用,因此不可能在两个并行运行的实例中操作UI 可以并行访问UI吗 代码:C# 并行编程:Can';无法并行访问UI?,c#,C#,我试图在wpf c#中创建一个函数的并行执行,该函数也在UI上运行操作。但是,当运行UI控件上的方法时,总会出现异常:调用线程无法访问此对象,因为其他线程拥有它。异常总是在正在运行的循环的第二个实例上调用,因此不可能在两个并行运行的实例中操作UI 可以并行访问UI吗 代码: do { if(listBox\u Copy.SelectedIndex{play(playcues,newroutedeventargs());}); 然后它在播放功能时崩溃 private void play(ob
do
{
if(listBox\u Copy.SelectedIndex{play(playcues,newroutedeventargs());});
然后它在播放功能时崩溃
private void play(object sender, System.Windows.RoutedEventArgs e)
{
Grid itemgrid = VisualTreeHelperExtensions.FindAncestor<Grid>(playcue);
...
}
private void play(对象发送方,System.Windows.RoutedEventArgs e)
{
Grid itemgrid=VisualTreeHelperExtensions.FindAncestor(播放提示);
...
}
无法从后台线程访问UI,所有更新必须在主线程上。您可以通过使用Dispatcher来实现这一点
像这样的
Action x = (Action)delegate {
//do my UI updating
};
Dispatcher.Invoke(x, new object[] { });
诀窍是使用
IProgress
向主线程报告更新。IProgress
构造函数接受将在主线程中运行的匿名函数,因此可以更新UI
引述自:
public async void StartProcessingButton\u单击(对象发送方,事件参数e)
{
//进度构造函数捕获我们的UI上下文,
//因此lambda将在UI线程上运行。
变量进度=新进度(百分比=>
{
textBox1.Text=百分比+“%”;
});
//DoProcessing在线程池上运行。
等待任务。运行(()=>DoProcessing(progress));
textBox1.Text=“完成!”;
}
公共无效数据处理(IProgress progress)
{
对于(int i=0;i!=100;++i)
{
Thread.Sleep(100);//CPU绑定的工作
如果(进度!=null)
进度报告(一);
}
}
现在,有一点自我提升:)我创建了一个IEnumerable
扩展来运行与事件回调并行的,可以直接修改UI。您可以在此处查看:
希望有帮助
Action x = (Action)delegate {
//do my UI updating
};
Dispatcher.Invoke(x, new object[] { });
public async void StartProcessingButton_Click(object sender, EventArgs e)
{
// The Progress<T> constructor captures our UI context,
// so the lambda will be run on the UI thread.
var progress = new Progress<int>(percent =>
{
textBox1.Text = percent + "%";
});
// DoProcessing is run on the thread pool.
await Task.Run(() => DoProcessing(progress));
textBox1.Text = "Done!";
}
public void DoProcessing(IProgress<int> progress)
{
for (int i = 0; i != 100; ++i)
{
Thread.Sleep(100); // CPU-bound work
if (progress != null)
progress.Report(i);
}
}