异步转换前的lambda pression委托类型System.Func&LT; T&GT ;? [英] Convert async lambda expression to delegate type System.Func<T>?
问题描述
我有一个便携式类库里面异步方法与此签名:
I have an async method inside a portable class library with this signature:
private async Task<T> _Fetch<T>(Uri uri)
它获取被投回为一个具体类型T的资源。
It fetches a resource that is cast back as a concrete type T.
我正在与第三方缓存库工作( Akavache ),需要一个 Func键&LT; T&GT
作为参数之一,曾尝试在这种方式这样做的:
I'm working with a 3rd party cache library (Akavache) that requires a Func<T>
as one of the parameters and have tried to do so in this manner:
await this.CacheProvider.GetOrCreateObject<T>(key,
async () => await _Fetch<T>(uri), cacheExpiry);
这导致错误:
无法转换异步拉姆达前pression委托类型 System.Func&LT; T&GT;
。一个异步的lambda前pression可以返回无效
,工作
或任务&LT; T&GT;
,其中没有一个是转换为 System.Func&LT; T&GT;
。
Cannot convert async lambda expression to delegate type '
System.Func<T>
'. An async lambda expression may returnvoid
,Task
orTask<T>
, none of which are convertible to 'System.Func<T>
'.
我试过 Func键&LT的各种排列; T&GT;
分配没有任何运气,我可以得到code工作的唯一方法是使 Func键&LT; T&GT;
阻塞: p>
I've tried various permutations of Func<T>
assignment without any luck, the only way I can get the code to work is to make the Func<T>
blocking:
await this.CacheProvider.GetOrCreateObject<T>(key,
() => _Fetch<T>(uri).Result, cacheExpiry);
这会造成死锁我的应用程序。
which deadlocks my app.
这是我误入歧途,其中任何指针?
Any pointers on where I'm going astray?
推荐答案
没有能做到。当有人需要一个 Func键&LT; T&GT; ˚F
你可以假设它的东西,如的结果= F调用()
- 即,它不知道异步行为。如果通过欺骗它。结果
像你这样 - 它会在UI线程死锁,因为它要安排后,code 的await
在UI线程(在_Fetch),但是你已经有阻止它。结果
。
No can do. When someone expects a Func<T> f
you can assume it will be invoked with something like result = f()
- i.e., it does not know about async behavior. If you cheat it by using .Result
like you have - it will deadlock on UI thread because it wants to schedule the code after await
(in _Fetch) on the UI thread, but you have already blocked it with .Result
.
异步拉姆达可以传递给动作
,因为它没有返回值 - 或 Func键&LT;任务&GT;
或 Func键&LT;任务&LT; T&GT;&GT;
。
Async lambda can be passed to Action
since it has no return value - or to Func<Task>
or Func<Task<T>>
.
看你的情况下, GetOrCreateObject
似乎调用 GetOrFetchObject
。其中的 GetOrFetchObject
重载接受 Func键&LT;任务&LT; T&GT;&GT;
。您可以尝试调用一个方法,你的异步拉姆达,看看它是否会有所帮助。
Looking at your case, the GetOrCreateObject
appears to be calling GetOrFetchObject
. One of the GetOrFetchObject
overloads accepts a Func<Task<T>>
. You can try calling that method with your async lambda and see if it helps.
这篇关于异步转换前的lambda pression委托类型System.Func&LT; T&GT ;?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!