递归方法对 UI 施加压力
Recursive Method Puts Strain on UI
我有一个使用 SendKeys.Send
的方法,使用 System.Threading.Thread.Sleep
等待几秒钟,然后 运行 使用另一种方法来检查像素的颜色,看它是否有变了。然后该方法再次 运行s,因为它被递归调用。
此方法需要能够 运行 数千次才能停止。 Winform 的 UI 似乎在 运行ning 时停止响应。
我试图实现一个后台工作者来减轻 UI 的压力。我将递归方法的代码移至 Do_Work
事件并使用 RunWorkerAsync
调用它,但它崩溃了,报告如下:
An exception of type 'System.InvalidOperationException' occurred in System.Windows.Forms.dll but was not handled in user code
Additional information: SendKeys cannot run inside this application because the application is not handling Windows messages.
将代码从 UI 移开的最佳方法是什么?我对后台工作人员不是很熟悉所以我可能做错了。
听起来像是 async
的情况。尝试将 Thread.Sleep()
替换为 Task.Delay()
.
async void Button_Click(object sender, RoutedEventArgs e)
{
await SendMyKeysAsync();
}
async Task SendMyKeysAsync()
{
while (thePixelIsStillRed)
{
SendKeys.Send("whatever");
await Task.Delay(TimeSpan.FromSeconds(1));
}
}
这种方法让 UI 线程可以在延迟期间自由地继续发送消息,而不会产生任何额外的线程。
您应该编写异步迭代方法,而不是同步递归方法。
private async void Foo()
{
while(ShouldKeepLooping())
{
SendKeys.Send(keyToSend);
await Task.Delay(timespan.FromSeconds(2));
}
}
使方法递归不会增加任何内容;使其迭代消除堆栈压力。通过使方法异步而不是同步,您不会阻塞 UI 线程。
我有一个使用 SendKeys.Send
的方法,使用 System.Threading.Thread.Sleep
等待几秒钟,然后 运行 使用另一种方法来检查像素的颜色,看它是否有变了。然后该方法再次 运行s,因为它被递归调用。
此方法需要能够 运行 数千次才能停止。 Winform 的 UI 似乎在 运行ning 时停止响应。
我试图实现一个后台工作者来减轻 UI 的压力。我将递归方法的代码移至 Do_Work
事件并使用 RunWorkerAsync
调用它,但它崩溃了,报告如下:
An exception of type 'System.InvalidOperationException' occurred in System.Windows.Forms.dll but was not handled in user code
Additional information: SendKeys cannot run inside this application because the application is not handling Windows messages.
将代码从 UI 移开的最佳方法是什么?我对后台工作人员不是很熟悉所以我可能做错了。
听起来像是 async
的情况。尝试将 Thread.Sleep()
替换为 Task.Delay()
.
async void Button_Click(object sender, RoutedEventArgs e)
{
await SendMyKeysAsync();
}
async Task SendMyKeysAsync()
{
while (thePixelIsStillRed)
{
SendKeys.Send("whatever");
await Task.Delay(TimeSpan.FromSeconds(1));
}
}
这种方法让 UI 线程可以在延迟期间自由地继续发送消息,而不会产生任何额外的线程。
您应该编写异步迭代方法,而不是同步递归方法。
private async void Foo()
{
while(ShouldKeepLooping())
{
SendKeys.Send(keyToSend);
await Task.Delay(timespan.FromSeconds(2));
}
}
使方法递归不会增加任何内容;使其迭代消除堆栈压力。通过使方法异步而不是同步,您不会阻塞 UI 线程。