将函数包装为异步任务

时间:2015-10-04 04:43:05

标签: c# .net async-await task-parallel-library

我有一个我想要包装的函数,以便我可以使用async / await模式:

wcfClientService.GetSomeString(parameter);

这是来自WCF客户端的调用,我正在尝试异步,但这并不重要(我知道WCF支持异步,但我们假设我们无法访问WCF代码)。

我正在尝试使用Task<T>.Factory.FromAsync方法包装方法,但似乎无法做到正确:

private Task<string> WrapWcfServiceAsyncTask(uint parameter)
{
    Func<uint, string> func = i => { return wcfClientService.GetSomeString(parameter); };

    var t = Task<string>.Factory.FromAsync(
                                           // What goes here?
                                          );
    return t;
}

或者甚至更好,有人可以编写一个方法,将方法作为参数,并为其包装并返回Task<T>吗?

2 个答案:

答案 0 :(得分:6)

您要做的是async over sync。你有一个同步操作,你想假装它是异步的。

您可以使用Task.Run

执行此操作
var result = await Task.Run(() => wcfClientService.GetSomeString(parameter));

但是,因为您只是将工作从一个ThreadPool线程卸载到另一个线程,所以它毫无意义。

如果你想要一个异步操作,它需要以某种方式开始异步,无论是使用async-await还是Begin / End等等。

如果您已经异步BeginGetSomeString / EndSomeString,则可以使用FromAsync将其转换为异步等待。

答案 1 :(得分:3)

如果使用现代版本的Visual Studio重新生成WCF代理,则默认情况下应生成Dynamic Partials。请注意,WCF服务根本不需要更改;它只是需要更新的客户端代理。

然后你可以用普通的await调用它的方法;没有Task.Run

private async Task<string> WrapWcfServiceAsyncTask(uint parameter)
{
  return await wcfClientService.GetSomeStringAsync(parameter);
}