c# blazor 避免在委托类型返回 'void' 时使用 'async' lambda

Posted

技术标签:

【中文标题】c# blazor 避免在委托类型返回 \'void\' 时使用 \'async\' lambda【英文标题】:c# blazor avoid using 'async' lambda when delegate type returns 'void'c# blazor 避免在委托类型返回 'void' 时使用 'async' lambda 【发布时间】:2022-01-14 19:27:21 【问题描述】:

我在 JetBrains Rider 中收到以下警告,但我找不到解决方法。 这是一个带有 .net 6 的 blazor WASM 项目。

当委托类型返回 'void' 时避免使用 'async' lambda

Razor 示例代码:

<Validation Validator="async e => await ValidateFieldAsync(e)">

示例代码c#:

protected async Task ValidateFieldAsync(ValidatorEventArgs args)

    // Some code with awaits etc.

Jetbrains 在此处描述此警告:

https://www.jetbrains.com/help/resharper/AsyncVoidLambda.html

但是解决此问题的最佳做法是什么?

感谢任何提示!

【问题讨论】:

【参考方案1】:

看起来 Resharper 在这里迷路了。警告不正确。

但无论如何你都可以改进这一点,

<Validation Validator="e => ValidateFieldAsync(e)">

只要 ValidateFieldAsync() 仍然返回 async Task 这仍然是异步的和可等待的,只是开销少了一点。 lambda 中的 ayncawait 添加了一个不需要的额外层。 它可能会阻止那个错误的警告,我现在无法检查。

当您不需要任何参数或 Blazor 可以自动添加它时,您可以按照 @MisterMagoo 的回答。

【讨论】:

"当您不需要 e 时,您可以按照 @MisterMagoo 的回答。"该声明暗示当您需要ValidatorEventArgs 时,您不应该遵循@MisterMagoo 的回答,对吧?不你错了。 ValidatorEventArgs 由框架自动传递给事件处理程序,这正是 Mister Magoo 使用 Validator="ValidateFieldAsync" 作为方法签名 protected async Task ValidateFieldAsync(ValidatorEventArgs args) 的原因 问题是关于 Resharper,并非所有参数都可以自动填充。 如果是这样,@Mister Magoo 的回答是错误的,我不应该赞成他的回答。我猜不是…… 我按照规定的方式对其进行了测试,这只给出了一个新的警告:“因为没有等待这个调用,所以在调用完成之前继续执行当前方法。考虑将'await'运算符应用于通话的结果。”我将在 jetbrains 跟踪器上打开一个错误报告,以消除似乎由错误显示的原始警告。 是的,这是给 Resharper 的。显然它不能“预测” Razor 生成的代码。不过,我仍然会一直使用简写形式。【参考方案2】:

这里根本不需要 lambda。

<Validation Validator="ValidateFieldAsync" >

<Validation Validator=@ValidateFieldAsync >

<Validation Validator=ValidateFieldAsync >

应该都行 - 这只是您对风格的偏好问题。

从这个方法返回一个任务是正确的。

【讨论】:

我使用了一个只有一个参数的坏样本,如果有多个参数,这是无法做到的。但在示例的上下文中,这是正确的。 确实如此。如果你的方法定义了多个参数,你应该使用lambada表达式,将这些参数传递给方法,并且不要在参数列表之前使用关键字async做这样的事情:Validator="@( (e) =&gt; await ValidateFieldAsync(e, index))",变量index,被您在代码中定义的内容... 确实最好问你想回答的问题。【参考方案3】:

当从 razor 调用函数时,不要调用 Task 函数。调用 void 函数,因为这是预期的。

<Validation Validator="e => ValidateFieldAsync(e)">

然后是实际代码:

protected async void ValidateFieldAsync(ValidatorEventArgs args)

    // Some code with awaits etc.

它仍然会异步运行,所以不用担心在 razor 调用代码中有 async

【讨论】:

这是一个糟糕的建议 - 您应该只对 EventHandler 使用 async void - 所有 Blazor EventCallbacks 在异步时都应该返回一个 Task。

以上是关于c# blazor 避免在委托类型返回 'void' 时使用 'async' lambda的主要内容,如果未能解决你的问题,请参考以下文章

C#控制台基础 返回类型为void的无参数委托与匿名方法

C#控制台基础 返回类型为void的 int 类型参数的委托与拉姆塔表达式

C# Action<T;和 Func<T;委托

没有返回类型的函数委托

从转换为void返回委托的匿名函数返回

C#委托初学