异步和并行执行功能

时间:2014-02-12 22:19:04

标签: c# windows-phone-7 windows-phone-8 async-await

我有一个功能:

int f1(int a)
{
    return a;
}

int f2(int a)
{
    return a*2;
}

我希望执行函数异步和并行,等待结果并求和结果。我可以使用代码

 var result1 = Task.Run(() => f1(5));
 var result2 = Task.Run(() => f2(10));

 await Task.WhenAll(result1, result2);

 int result = result1.Result + result2.Result;

很酷。但是,如果我的函数使用回调

,该怎么办?
void f1(Action<int> action, int a)
{
    action.Invoke(a);
}

void f2(Action<int> action, int a)
{
    a = a*2;
    action.Invoke(a);
}

f1(result => Console.WriteLine("result1 = {0}", result), 5);
f2(result => Console.WriteLine("result2 = {0}", result), 10);

我不能重写这个函数,这个函数在其他代码中使用。在这种情况下,我可以解决我的代码不像地狱的问题吗?

2 个答案:

答案 0 :(得分:5)

var tcs1 = new TaskCompletionSource<int>();
var tcs2 = new TaskCompletionSource<int>();

f1( (x) =>  { tcs1.SetResult(x);  }, 5);
f2( (x) =>  { tcs2.SetResult(x);  }, 10);

var results = await Task.WhenAll(tcs1.Task, tcs2.Task);
int result = results[0] + results[1];

答案 1 :(得分:3)

您可以使用TaskCompletionSource类创建一个任务,该任务表示基于回调的异步方法(或基于事件的异步方法或任何其他非基于Task的异步方法)的完成在那里):

var f1CompletionSource = new TaskCompletionSource<int>();
var f2CompletionSource = new TaskCompletionSource<int>();
Task.Run(() => foo.f1(n => f1CompletionSource.TrySetResult(n), 5));
Task.Run(() => foo.f2(n => f2CompletionSource.TrySetResult(n), 10));

await Task.WhenAll(f1CompletionSource.Task,
    f2CompletionSource.Task);

int result = f1CompletionSource.Task.Result +
    f2CompletionSource.Task.Result;

此处不清楚您是否希望通过f1调用f2Task.Run。你提供的方法是同步完成的,而不是异步的,但如果你在这里建模的实际方法是异步工作,那么就不需要Task.Run