Skip to content

Instantly share code, notes, and snippets.

@jhoerr
Last active December 11, 2015 05:26
Show Gist options
  • Save jhoerr/8db3fc45f60774ff735d to your computer and use it in GitHub Desktop.
Save jhoerr/8db3fc45f60774ff735d to your computer and use it in GitHub Desktop.
// LINQPad
void Main()
{
new Demo().Nested(1).Result.Dump();
new Demo().Continuation(1).Result.Dump();
new Demo().Variables(1).Result.Dump();
new Demo().NestedAlt(1).Result.Dump();
}
// Define other methods and classes here
public static class GenericExtensions
{
public static Tout Map<Tin,Tout>(this Tin @this, Func<Tin, Tout> fn) => fn(@this);
}
public class Demo
{
public async Task<int> F(int x) => await Task.FromResult(x + 1);
public async Task<int> G(int x) => await Task.FromResult(x * 2);
public async Task<int> H(int x) => await Task.FromResult(x + 3);
public async Task<int> Nested(int x) => await (await (await H(x)).Map(G)).Map(F);
public async Task<int> Continuation(int x)
{
return await (await H(x)
.ContinueWith(t => G(t.Result))
.ContinueWith(t => F(t.Result.Result)));
}
public async Task<int> Variables(int x)
{
var result1 = await H(x);
var result2 = await G(result1);
return await F(result2);
}
public async Task<int> NestedAlt(int x)
{
return await GPrime(x) + 1;
}
public async Task<int> GPrime(int x)
{
return await H(x) * 2;
}
}
@davefancher
Copy link

I think you can get away with just one more extension method:

public static async Task<TOut> MapAwait<TIn, TOut>(
    this Task<TIn> @this,
    Func<TIn, Task<TOut>> fn) => await fn(@this.Result);

Then you can chain the methods together like so:

var d = new Demo();

1
    .Map(d.H)
    .MapAwait(d.G)
    .MapAwait(d.F)
    .Result
    .Dump();

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment